Java 8 readily receive the result of an intermediate stream operation

Given the following code:

List<String> list = Arrays.asList("a", "b", "c");
        list.stream()
        .map(s -> s + "-" + s)                 //"a-a", "b-b", "c-c"
        .filter(s -> !s.equals("b-b"))         //"a-a", "c-c"
        .forEach(s -> System.out.println(s));

      

map

and filter

are intermediate operations, and forEach

- terminal operation. Only after performing the terminal operation can we get the result of data transformation.

Is there a way to make the evaluator be more impatient and have some kind of intermediate result - without breaking the chain of operations of the flow? For example, I want to have a list "aa", "bb", "cc" (which would be the result of the first intermediate operation).

+3


source to share


3 answers


You can use peek

:

List<String> allPairs = new ArrayList<>();
List<String> list = Arrays.asList("a", "b", "c");
    list.stream()
    .map(s -> s + "-" + s)                 //"a-a", "b-b", "c-c"
    .peek(allPairs::add)
    .filter(s -> !s.equals("b-b"))         //"a-a", "c-c"
    .forEach(s -> System.out.println(s));

      



Thus, calculations will still not start before the terminal operation, but you can "intercept" the contents of the stream at any time and use it in any way.

Beware, however, if your terminal's operation is short-circuited (for example findFirst

): thus, not all elements can be passed to peek

.

+7


source


Ok ... if I understand your question correctly, you need to apply a terminal operation before filtering the predicate not equals "b-b"

. Then you must call the .stream()

intermediate result and filter:



List<String> list = Arrays.asList("a", "b", "c");
list.stream()
    .map(s -> s + "-" + s)           //"a-a", "b-b", "c-c"
    .collect(Collectors.toList())    //intermediate result
    .stream()
    .filter(s -> !s.equals("b-b"))   //"a-a", "c-c"
    .forEach(s -> System.out.println(s));

      

+5


source


As Anton and Coco already said, you can add your own collector, or use the Stream.collect method with supplier, battery and combiner parameters:

    List<String> intermediateList = new ArrayList<>();
    List<String> list = Arrays.asList("a", "b", "c");
    list.stream().map(s -> s + "-" + s) // "a-a", "b-b", "c-c"
            .collect(() -> intermediateList, // supplier returns your intermediateList
                    (l, x) -> l.add(x), // accumulator - adds the element to your list
                    (l1, l2) -> {} // l1 and l2 are the same list, i guess - nothing to combine
            ) 
            .stream().filter(s -> !s.equals("b-b")) // "a-a", "c-c"
            .forEach(s -> System.out.println(s));

      

0


source







All Articles