Given a list of items with properties, I am trying to get the last item to appear with a maximum value of said property.
For example, for the following list of objects:
t i
A: 3
D: 7 *
F: 4
C: 5
X: 7 *
M: 6
I can get one of the Things with the highest i
:
Thing t = items.stream()
.max(Comparator.comparingLong(Thing::getI))
.orElse(null);
However, this will get me Thing t = D
. Is there a clean and elegant way of getting the last item, i.e. X
in this case?
One possible solution is using the reduce
function. However, the property is calculated on the fly and it would look more like:
Thing t = items.stream()
.reduce((left, right) -> {
long leftValue = valueFunction.apply(left);
long rightValue = valueFunction.apply(right);
return leftValue > rightValue ? left : right;
})
.orElse(null);
The valueFunction
now needs to be called nearly twice as often.
Other obvious roundabout solutions are:
Remove the equals option (don't return 0 if the compared numbers are equal, return -1 instead) from the comparator (ie. write your own comparator that doesn't include an equals option):
Thing t = items.stream()
.max((a, b) -> a.getI() > b.getI() ? 1 : -1)
.orElse(null);