Stream 사용시 주의사항

2023. 7. 5. 01:02Java/일반

Stream 재사용 문제

IntStream stream = IntStream.of(1, 2, 3);
stream.forEach(x -> System.out.println(x));    //첫번째 stream 사용

stream.forEach(x -> System.out.println(x));    //두번째 stream 사용

stream은 오직 한번만 소비할 수 있기 때문에 두 번째 사용할 경우 IllegalStateException이 발생할 수 있습니다.

Stream의 동작 순서

Arrays.stream(new String[] {"c", "python", "java"})
    .filter(word -> {
        System.out.println("filter method : " + word);
        return word.length() > 3;
    })
    .map(word -> {
        System.out.println("map method : " + word);
        return word.substring(0, 3);
    })
    .findFirst();

실행결과

Stream은 3개의 요소에 대해서 각 3번씩 호출이 이루어질 것 같지만 요소 하나씩 각각 모든 파이프라인을 수행합니다. 실제로는 다음과 같은 단계로 수행이 이루어집니다.

  • 'c': filter가 실행되지만 조건이 맞지 않아 다음으로 진행되지 않음
  • 'python': filter가 실행되고 조건이 맞아 다음으로 진행 > map에 의해 substring 수행 > findFirst수행
  • 'java': 앞의 'python'이 findFirst까지 수행하여 어떤 연산도 수행하지 않음

Stream.foreach는 loop가 아님

코드1

for (int i = 0; i < 5000; i++) {
  if (i > 5) {
    break;
  }
  System.out.println(i);
}

코드2

public static void foo() {
    IntStream.range(1, 5000).forEach(i -> {
        if (i > 5) {
            return;
        }
        System.out.println(i);
    });
}

코드1과 코드2 모두 동일하게 1~5를 출력하지만, Stream.foreach를 사용한 식은 1부터 5000까지 무조건 반복하여 수행합니다.

728x90

'Java > 일반' 카테고리의 다른 글

JPA  (0) 2023.01.22
Java Serialize  (0) 2022.11.27
String Pool  (0) 2022.07.22
Netty  (1) 2022.05.26
JIT Compiler  (0) 2021.10.08