Сегодня у нас задачка с подвохом для тех, кто пишет на Java. Какой результат будет выведен в консоль? Пишите в комментариях!
import java.util.stream.Stream; public class Main { public static void main(String[] args) { Stream<Integer> stream = Stream.of(1, 2, 3, 4, 5); Integer result = prepareStream(stream); System.out.printf("Result after stream processing: %s%n", result); } private static Integer prepareStream(Stream<Integer> stream) { System.out.printf("Incoming stream with: %d elements%n", stream.count()); return stream .map(integer -> integer++ + ++integer) .filter(integer -> integer % 3 == 0) .reduce(0, Integer::sum); } }
Дальше будет решение, поэтому если не хотите спойлеров — не читайте!
.
.
.
Подвох в том, что будет выброшено исключение:
Exception in thread "main" java.lang.IllegalStateException: stream has already been operated upon or closed at java.base/java.util.stream.AbstractPipeline.<init>(AbstractPipeline.java:203) at java.base/java.util.stream.ReferencePipeline.<init>(ReferencePipeline.java:96) at java.base/java.util.stream.ReferencePipeline$StatelessOp.<init>(ReferencePipeline.java:800) at java.base/java.util.stream.ReferencePipeline$3.<init>(ReferencePipeline.java:191) at java.base/java.util.stream.ReferencePipeline.map(ReferencePipeline.java:190) at Main.prepareStream(Main.java:16) at Main.main(Main.java:7)
Исключение выбрасывается из-за того, что при выводе в консоль лога с количеством элементов стрима мы использовали операцию stream.count(), которая является терминальной и делает дальнейшее использование стрима невозможным.
System.out.printf("Incoming stream with: %d elements%n", stream.count());
Ну а после того, как мы избавимся от лога, который нам все ломает, правильный ответ будет — 18.
С учетом postfix и prefix инкремента числа в каждой итерации мы получаем:
.map(1 → 1 + 3)...(5 → 5 + 7)
Потом после фильтрации по делению на 3 без остатка в стриме остаются числа 6 и 12. И при помощи операции reduce() находим сумму этих чисел.
