Groovy: sort hash keys by values value
groovy, hash, sorting
Solution
Short answer: Yes, the `keySet()` method will always return an ordered `java.util.List`.
Long answer: That's a bit hard to prove as we have to look at some source code.
Examination starts in `groovy.runtime.DefaultGroovyMethods` where the `public static <K, V> Map<K, V> sort(Map<K, V> self, Closure closure)` method returns a `java.util.LinkedHashMap`, which is ordered.
The `LinkedHashMap`'s `Set<K> keySet()` method is defined in the `java.util.HashMap` class and returns an `Iterator` by calling the `Iterator<K> newKeyIterator()` method, which is overriden in the `LinkedHashMap` class][4]. It returns a `LinkedHashMap$KeyIterator`, which [defines the `K next()` method that internally calls the `Entry<K,V> nextEntry()` method, which returns an `Entry` that has been defined in the `LinkedHashMap$Entry.after` field.
Finally, one can see in the `LinkedHashMap$Entry.addBefore(Entry<K,V> existingEntry)` method that the `LinkedHashMap$Entry.after` field is set in an ordered manner.
Oh my ... I had linked each statement I did to the corresponding source code in `groovy.runtime.DefaultGroovyMethods`, `java.util.HashMap` and `java.util.LinkedHashMap`, summing up to 10 hyperlinks. Unfortunately, as a newbie at Stackoverflow, I'm just allowed to post one, having to remove most links ... Sorry.
Problem
I want to sort a hash of key->value by the values , and get the list of the sorted keys. This seems to work: ``` groovy> def map = [a:5, b:3, c:6, d:4].sort { a, b -> a.value <=> b.value }.keySet() groovy> println map [b, d, a, c] ``` but will it always work? I don't know if the iterator that builds the keySet() will always iterate them by order. Thanks!