Consider the following code fragment. The result of the entire pipeline is "ab" in all cases, as expected.
Stream.of("a", "ab", "abc", "abcd")
// .sorted() // uncomment and what follows becomes eager
.filter(s -> s.contains("b"))
.peek(s -> System.out.println("PEEK: " + s))
.findFirst()
.orElse("X");
With sorted() commented out, findFirst() is fully lazy and so the output from peek is:
PEEK: ab
However, with sorted() uncommented, the output changes to:
PEEK: ab
PEEK: abc
PEEK: abcd
All the elements appear to be sent downstream from sorted() even though findFirst() is only interested in the first one. This could be a performance problem if the operations after sorted(), such as filtering, are expensive.
Workaround: collect the sorted results into a collection and run the rest of the pipeline from that collection.
See also: http://stackoverflow.com/q/23419223/1441122