Предположим, что у вас есть такой метод, который вычисляет максимум Collection для некоторого ToIntFunction:
static <T> void foo1(Collection<? extends T> collection, ToIntFunction<? super T> function) {
if (collection.isEmpty())
throw new NoSuchElementException();
int max = Integer.MIN_VALUE;
T maxT = null;
for (T t : collection) {
int result = function.applyAsInt(t);
if (result >= max) {
max = result;
maxT = t;
}
}
// do something with maxT
}
С Java 8 это можно перевести в
static <T> void foo2(Collection<? extends T> collection, ToIntFunction<? super T> function) {
T maxT = collection.stream()
.max(Comparator.comparingInt(function))
.get();
// do something with maxT
}
Недостатком новой версии является то, что function.applyAsInt вызывается повторно для одного и того же значения T. (В частности, если коллекция имеет размер n, foo1 вызывает applyAsInt n раз, тогда как foo2 вызывает его 2n - 2 раз).
Недостатки первого подхода заключаются в том, что код менее ясен, и вы не можете его модифицировать для использования parallelism.
Предположим, вы хотели сделать это, используя параллельные потоки и только для вызова applyAsInt один раз для каждого элемента. Может ли это быть написано простым способом?