The behavior of the Stream.generate method when passing a provider argument <Stream <T>>
After reading this question and one of my answers, I decided to independently perform some tests. To my surprise, I came to a situation that looks rather strange.
Here is the code:
public class InfiniteRepeatingStream {
    public static void main(String[] args) {
        Stream<Integer> s1 = repeatFromSupplier(() -> Stream.of(1, 2, 3));
        s1.sequential().limit(10).forEachOrdered(System.out::print);
        System.out.print("\n----------------\n");
        Stream<Integer> s2 = repeatFromStream(Stream.of(1, 2, 3));
        s2.sequential().limit(10).forEachOrdered(System.out::print);
    }
    static <T> Stream<T> repeatFromSupplier(Supplier<Stream<T>> supplier) {
        return Stream.generate(supplier).flatMap(s -> s);
    }
    static <T> Stream<T> repeatFromStream(Stream<T> stream) {
        return Stream.generate(() -> stream).flatMap(s -> s);
    }
}
As you can see, the difference between the methods repeatFromSupplierand repeatFromStreamis lying on his argument and that is passed to the method Stream.generate.
While the method repeatFromSupplierreceives the type argument Supplier<Stream<T>>and passes this argument directly to the method Stream.generate, the method repeatFromStreamreceives the type argument Stream<T>and creates an Supplier<Stream<T>>expression from the built-in lambda () -> streamthat is immediately passed to the method Stream.generate.
, , , .
repeatFromSupplier repeatFromStream. , , repeatFromSupplier ( 1231231231), repeatFromStream 123 IllegalStateException: stream has already been operated upon or closed.
, . . , -.