How to sort a map with the key first and sort the values as well.
Map<String, List<String>> myMap = new HashMap<>();
myMap.put("Apple", Arrays.asList("iphone", "imac"));
myMap.put("Samsung", Arrays.asList("galaxys", "galaxyz"));
myMap.put("LG", Arrays.asList("ultra", "tab"));
//sort logic
Sort with the key first {Apple, LG, Samsung} and then sort the values based on the key.
Result:
imac, iphone, tab, ultra, galaxys, galaxyz
It's easier to work out stream problems by making a plan. An example one for this problem would be:
Stream<Map.Entry<String, List<String>>>
)Stream<List<String>>
)Stream<String>
)List<String>
)You'd first have to convert the map to an entrySet
to allow you to stream over the Map.Entry
entries. Then we can get the lists sorted via the map key with .sorted(Map.Entry.comparingByKey())
and .map(Map.Entry::getValue)
.
Once we have the lists in sorted order, the elements within are not sorted. So we then need to flatten them (go from a Stream<List<String>>
to Stream<String>
containing the elements of the lists) in sorted order: .flatMap(list -> list.stream().sorted())
Resulting in the code:
List<String> result = myMap.entrySet().stream() // Step 1
.sorted(Map.Entry.comparingByKey()) // Step 2
.map(Map.Entry::getValue) // Step 3
.flatMap(list -> list.stream().sorted()) // Step 4+5
.collect(Collectors.toList()); // Step 6
You can also skip the mapping from Map.Entry::getValue
, doing .flatMap(entry -> entry.getValue().stream().sorted())
directly, but it's a bit less clear what's going on.