Dev./java
[Java] 스트림(Stream)
인쥭
2020. 10. 14. 10:08
반응형
다음의 링크로부터 훨씬 자세한 내용을 확인하실 수 있습니다 :
0. Collection과 stream 메소드
- Java에서 제공하는 컬렉션들의 조상인 Collection에는 아래와 같이 Stream 메소드가 정의되어 있다.
- 따라서 인터페이스인 Collection을 구현한 모든 클래스는 stream()을 통해 스트림을 생성할 수 있다.
public interface Collection<E> extends Iterable<E> {
/*
중략
*/
default Stream<E> stream() {
return StreamSupport.stream(spliterator(), false);
}
/*
후략
*/
}
1. Stream이란?
- Java 8에 Stream이 도입되기 전에는 Collection으로부터 구현된 인스턴스를 다루기 위해 for / forEach문을 사용해야만 했다.
- 이러한 방식은 코드가 복잡해질수록 코드의 양이 많아지고 가독성이 떨어지기 쉬웠다고 함.
- 스트림은 Collection 인스턴스에 여러 함수를 조합하여 원하는 결과를 필터링하거나 가공하는 방법을 제공한다.
- 여러 함수의 조합에서 람다식을 사용하여 코드 양을 줄일 수 있으며, 보다 간결한 코딩을 가능케 한다. 때문에 스트림은 람다식과 밀접한 관련이 있다!
2. Stream 사용하기
- Stream은 크게 세가지 단계로 나눠 생각해볼 수 있다.
- 생성 : Stream 인스턴스 생성
- 가공 : 필터링 / 매핑 등을 통한 중간 가공
- 결과 : 최종적으로 결과를 만들어 반환
i). 생성하기
// 배열 스트림
String[] tmpArray = new String[]{"a", "b", "c"};
Stream<String> tmpStream = Arrays.stream(tmpArray);
Stream<String> partOfTmpStream = Arrays.stream(tmpArray, 1, 2); // 배열의 일부만 사용
// 컬렉션 스트림
// 컬렉션 인터페이스를 구현한 Collection, List, Set 등은 .stream() 메소드를 통해 스트림을 만들 수 있다.
List<String> tmpList = Arrays.asList("a", "b", "c");
Stream<String> tmpStream = tmpList.stream();
// 빈 스트림
Stream<Object> tmpStream = Stream.empty();
ii). 가공하기
List<String> strList = Arrays.asList("abc", "bcd", "cde", "def", "efg");
// filter는 각 요소를 평가
Stream<Integer> tmpStream = strList.stream().filter(str -> str.contains("e"));
// map은 Stream 내부의 각 요소를 변환
Stream<Integer> tmpStream = strList.stream().map(String::toUpperCase);
iii). 결과 생성
// Collect는 종료 작업으로서 Collector 타입의 인자를 받아 처리
List<TmpClass> tmpList = Arrays.asList(
new TmpClass("tmp0"),
new TmpClass("tmp1"),
new TmpClass("tmp2"),
new TmpClass("tmp3")
);
// 아래의 Collectors.toList()는 tmpList의 Stream으로부터 getter를 활용한 리스트를 반환
List<String> toListTest =
tmpList.stream()
.map(TmpClass::getAttr)
.collect(Collectors.toList());
번외. stream().map()을 통해 생성자의 매개변수가 하나인 DTO 생성하기
List<String> tmpStr = Arrays.asList("abc", "cde");
// TmpClass는 생성자의 매개변수가 하나이며, 아래의 두 내용은 같은 의미를 갖는다.
List<String> firstStr = tmpStr.stream()
.map(x -> new TmpClass(x))
.collect(Collectors.toList());
List<String> secondStr = tmpStr.stream()
.map(TmpClass::new)
.collect(Collectors.toList());