Reputation: 19099
I have an array of docker image tags values in string format. I was to sort the values in numerical and display in descending order.
How can I change the below code to sort in numerical order?
class Sorting {
def static main(args) {
def d=["1.0.25.3306",
"0.7.25.3307",
"40.56.25.3308",
"8.78.25.3309",
"4.12.25.3310",
"6.23.25.3311",
"23.45.25.3312",
"12.89.25.3313",
"7.0.25.3314",
"20.5.25.3315",
"8.67.25.3316",
]
println d.sort()
}
}
Upvotes: 1
Views: 350
Reputation: 42184
You can use sort
(or toSorted
) methods with a custom comparator. Keep in mind, that sort(Closure comparator)
mutates the input list, so you may want to use either:
sort(boolean mutate, Closure closure)
toSorted(Closure closure)
method that creates a new list and keeps the input list unmodified.
For the comparator, you get every version string, tokenize it by .
character, and transform every token to the integer value. Without this part, you will keep comparing strings. Let me show you it by example:
def d = ["1.0.25.3306",
"0.7.25.3307",
"40.56.25.3308",
"8.78.25.3309",
"4.12.25.3310",
"6.23.25.3311",
"23.45.25.3312",
"12.89.25.3313",
"7.0.25.3314",
"20.5.25.3315",
"8.67.25.3316",
]
def result = d.toSorted { a, b ->
def (a1, a2, a3, a4) = a.tokenize(".")*.toInteger()
def (b1, b2, b3, b4) = b.tokenize(".")*.toInteger()
return a1 <=> b1 ?: a2 <=> b2 ?: a3 <=> b3 ?: a4 <=> b4
}
result.each { println it }
In the comparator closure, we take every version string and we tokenize it by the .
character. Here we capture the output of tokenize()
method into multiple variables using multiple assignment, so each part gets assigned to its own variable. Then we use spread operator *.
to call toInteger()
on each token, which by default is still a type of String
. Once we represented two version strings to that form, we can use compare operator <=>
to compare every part of the version. We use Elvis operator ?:
to compare the following part if the a
and b
in the current part has the same numeric value. If you run this example, you will get something like this in the output console.
0.7.25.3307
1.0.25.3306
4.12.25.3310
6.23.25.3311
7.0.25.3314
8.67.25.3316
8.78.25.3309
12.89.25.3313
20.5.25.3315
23.45.25.3312
40.56.25.3308
Upvotes: 1