Предположим, что у вас есть такой метод, который вычисляет максимум 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
один раз для каждого элемента. Может ли это быть написано простым способом?