Да, есть способ сделать это, но с некоторыми ограничениями.
Stream<Integer> infiniteStream = Stream.iterate(0, x -> new Integer(x + 1));
Iterator<Integer> iter = infiniteStream.iterator();
Integer zero = iter.next();
Integer one = iter.next();
В качестве альтернативы,
Stream<Integer> infiniteStream = Stream.iterate(0, x -> new Integer(x + 1));
Spliterator<Integer> spliterator = infiniteStream.spliterator();
spliterator.tryAdvance(i -> System.out.println(i)); // zero
spliterator.tryAdvance(i -> System.out.println(i)); // one
Учитывая в Stream
, можно получить Iterator
или Spliterator
от него, или запросить ли это параллельный поток, и т.д. Они определяются на интерфейсе BaseStream
, суперинтерфейс Stream
, что делает их немного простыми.
В этом случае мы знаем поток бесконечен, поэтому нет необходимости вызывать hasNext()
метод итератора или проверить возвращаемое значение Spliterator в tryAdvance()
ограничения является, что оба iterator()
и spliterator()
методов Stream
: Операции с терминалами, что означает, что после их вызова возвращенный Iterator или Spliterator имеет эксклюзивный доступ к значениям, представленным Stream. Дальнейшие операции над потоком (такие как filter
или map
и т. Д.) Не допускаются и будут выполняться с IllegalStateException
.
Если вы хотите, чтобы слезть первые пару элементов, а затем возобновить обработку потока, вы можете превратить spliterator обратно в поток таким образом:
Stream<Integer> stream2 = StreamSupport.stream(spliterator, false);
Это вероятно, будет работать нормально для некоторых вещей, но я Не уверен, что я рекомендую эту технику в целом. Я думаю, что он добавляет несколько дополнительных объектов и, следовательно, дополнительные вызовы методов на пути создания следующего элемента.
Редакционные комментарии (не относящиеся к данному вопросу):
- Не используйте
new Integer(val)
. Вместо этого используйте Integer.valueOf(val)
, который будет повторно использовать целое число в штучной упаковке, если оно доступно, что обычно справедливо для значений в диапазоне от -128 до 127.
- Вы можете использовать
IntStream
вместо Stream<Integer>
, который полностью избегает боксерских накладных расходов. Он не имеет полного дополнения к потоковым операциям, но имеет iterate()
, который выполняет функцию, которая работает с примитивными значениями int
.
Вы хотите на самом деле использовать удаленные элементы, или просто отбросьте их? Для последнего «.skip (n)» - это способ сделать это. –