Reputation: 119
I have a list that which looks like this: [3 : [Reasonable product ], 5 : [Great ]]
I want to sort (using streams) this list by the number before :
.
The list it has to look like this:
[5 : [Great ], 3 : [Reasonable product ]]
My code looks like this:
return ratingsForProduct.stream().sorted().collect(Collectors.toList());
I don't know how to use lambda function or what I have to put as parameter to sorted().
Upvotes: 2
Views: 6705
Reputation:
I think it's inefficient to convert a string to an integer each time strings are compared.
Try this.
List<String> result = list.stream()
.map(string -> new Object() {
int key = Integer.valueOf(string.substring(0, string.indexOf(":")).trim());
String value = string;
})
.sorted(Comparator.comparing(obj -> obj.key, Comparator.reverseOrder()))
.map(obj -> obj.value)
.collect(Collectors.toList());
or
List<String> result = list.stream()
.map(string -> Map.entry(Integer.valueOf(string.substring(0, string.indexOf(":")).trim()), string))
.sorted(Comparator.comparing(Entry::getKey, Comparator.reverseOrder()))
.map(Entry::getValue)
.collect(Collectors.toList());
Upvotes: 1
Reputation: 40034
List<String> list = new ArrayList<>(
List.of("3 : [Reasonable product ]", "5 : [Great ]"));
The comparator simply parses the number at the start of the string until a space is encountered. This will work for any size number within the range of an integer. You can use a stream or Collections.sort()
;
Comparator<String> comp = Comparator.comparing(
a -> Integer.valueOf(a.substring(0,a.indexOf(" "))),
Comparator.reverseOrder());
list = list.stream().sorted(comp)
.collect(Collectors.toList());
System.out.println(list);
prints
[5 : [Great ], 3 : [Reasonable product ]]
Upvotes: 1
Reputation: 40038
You can pass the custom Comparator to sort descending order by extracting integer from every string
List<String> sortedList = list.stream()
.sorted(Comparator.<String>comparingInt(s->Integer.parseInt(s.split(":")[0].trim())).reversed())
.collect(Collectors.toList());
or you can also use Collections.sort
Collections.sort(list,Comparator.<String>comparingInt(s->Integer.parseInt(s.split(":")[0].trim())).reversed());
Upvotes: 4
Reputation: 5232
If you can be sure of the format of list items, you can write your own comparator:
Collections.sort(ratingsForProduct, (a, b) -> {
return Integer.parseInt(b.substring(0, b.indexOf(':'))) -
Integer.parseInt(a.substring(0, a.indexOf(':')));
});
We use substring(0, indexOf(':'))
instead of charAt(0)
to handle values greater than 10. If you wanted to sort in ascending order, you would change the comparator to substract b from a (instead of a from b as it is currently).
Upvotes: 1