스트림의 연산

스트림이 제공하는 기능은 ? 중간 연산최종 연산이 있다.

 

중간 연산 : 연산결과가 스트림인 연산. 반복적으로 적용가능

최종 연산 : 연산결과가 스트림이 아닌 연산. 단 한번만 적용가능 (스트림의 요소를 소모)


중간 연산

Stream<T> distinct() - 중복 제거

Stream<T> filter(Predicate<T> predicate) - 조건에 안 맞는 요소 제외

Stream<T> limit(long maxSize) - 스트림의 일부를 잘라낸다

Stream<T> skip(long n) - 스트림의 일부를 건너 뛴다

Stream<T> peek(Consumer<T> action) - 스트림의 요소에 작업수행

 

Stream<T> sorted()

Stream<T> sorted(Comparator<T> comparator) 스트림의 요소를 정렬한다.

 

스트림의 요소를 변환

Stream<R> map(Function<T,R> mapper)

DoubleStream mapToDouble(ToDoubleFunction<T> mapper)

IntStream mapToInt(ToIntFunction<T> mapper)

LongStream mapToLong(ToLongFunction<T> mapper)

Stream<R> flatMap(Function<T,Stream<R>> mapper)

DoubleStream flatMapToDouble(Function<T.DoubleStream> m)

IntStream flatMapToInt(Function<T, IntStream> m)

LongStream flatMapToLong(Function<T,LongStream> m)

 


최종 연산

void forEach(Consumer<? super T> action>

void forEachOrdered(Consumer<? super T>action) - 각 요소에 지정된 작업 수행

(Ordered 붙으면 순서 유지됨, 병렬 스트림이여도)

 

long count() - 스트림의 요소의 개수 반환

 

Optional<T> max (Comparator<? super T> comparator)        

Optional<T> min (Comparator<? super T> comparator)

스트림의 최대값/최소값을 반환

스트림의 요소 하나를 반환

 

Optional<T> findAny() //아무거나 하나

Optional<T> findFirst() //첫번째 요소

 

주어진 조건을 모든 요소가 만족시키는지, 만족시키지 않는지 확인

boolean allMatch(Predicate<T> p) // 모두 만족 하는지

boolean anyMatch(PredicaAte<T> p ) // 하나라도 만족하는지

boolean nonMatch(Predicate<> p) // 모두 만족하지 않는지

 

스트림의 모든 요소를 배열로 반환

Object[] toArray()    

A[] toArray(IntFunction<A[]> generator)

 

스트림의 요소를 하나씩 줄여가면서(리듀싱) 계산한다.

Optional<T> reduce(BinaryOperator<T> accumulator)

T reduce (T identity, BinaryOperator<T> accumulator)

U reduce (U identity, BiFunction<U,T,U> accumulator, BinaryOperator<U> combiner)

 

스트림의 요소를 수집한다. 주로 요소를 그룹화하거나 분할한 결과를 컬렉션에 담아 반환하는데 사용된다.

R collect(Collector<T,A,R> collector)

R collect(Supplier<R> supplier, BiConsumer<R,T> accumulator, BiConsumer<R,R> combiner)


자세히 살펴보자😀

스트림 자르기 - skip(), limit()

Stream<T> skip (long n) // 앞에서부터 n개 건너뛰기

Stream<T> limit(long maxSize) // maxSize 이후의 요소는 잘라냄

 

예시 )

IntStream intStream = IntStream.rangeClosed(1, 10); // 12345678910

intStream.skip(3).limit(5).forEach(System.out::print); // 45678


스트림의 요소 걸러내기 - filter(), distinct()

Stream<T> filter(Predicate<? super T> predicate) // 조건에 맞지 않는 요소 제거

Stream<T> distinct() // 중복제거

 

예시 )

IntStream intStream = IntStream.of(1,2,2,3,3,3,4,5,5,6);

intStream.distinct().forEach(System.out::println); // 123456

 

IntStream intStream = IntStream.rangeClosed(1, 10); // 12345678910

intStream.filter(i->i%2==0).forEach(System.out::print); // 246810

                2의 배수 제거

intStream.filter(i->i%2!=0 && i%3!=0).forEach(System.out::print);

intStream.filter(i->i%2!=0).filter(i->i%3!=0).forEach(System.out::print);

                   중간 연산

2의 배수 빼고, 3의 배수빼면 1,5,7만 남음.


스트림 정렬하기 - sorted()

Stream<T> sorted() // 스트림 요소의 기본 정렬(Comparable)로 정렬

Stream<T> sorted(Comparator<? super T> compartor) // 지정된 Comparator로 정렬

 

strStream.sorted() 기본 정렬

strStream.sorted(Comparator.naturalOrder()) 같은 기본 정렬임 안에 생략되어 있는 것

strStream.sorted((s1,s2) -> s1.compareTo(s2)); // 람다식도 가능

strStream.sorted(String::compareTo); // 위와 동일함

출력 결과 대문자 먼저 나온다
CCaaabccdd

::는 뭐지? 어떻게 쓰는걸까? 궁금해서 검색 후 메소드 참조에 정리할 것임.

 

strStream.sorted(Comparator.reverseOrder()) // 기본 정렬의 역순

strStream.sorted(Comparator.<String>naturalOrder().reversed())

ddccbaaaCC

strStream.sorted(String.CASE_INSENSITIVE_ORDER) // 대소문자 구분안함

aaabCCccdd      대문자가 먼저 나온다. CCcc reverse 여서 ccCC가 나올것 같지만..😑

strStream.sorted(String.CASE_INSENSITIVE_ORDER.reversed()) 

ddCCccbaaa

strStream.sorted(Comparator.comparing(String::length)) // 길이 순 정렬

strStream.sorted(Comparator.comparingInt(String::length)) // no 오토박싱

bddCCccaaa

strStream.sorted(Comparator.comparing(String::length).reversed()) 

aaaddCCccb

- Comparator의 comparing()으로 정렬 기준을 제공

comparing(Function<T, U> keyExtractor)

comparing(Function<T, U> keyExtractor, Comparator<U> keyComparator)

 

studentStream.sorted(Comparator.comparing Student::getBan)) // 반별로 정렬

                   .forEach(System.out::println);

 

- 추가 정렬 기준을 제공할 때는 thenComparing()을 사용

thenComparing(Comparator<T> other)

thenComparing(Function<T, U> keyExtractor)

thenComparing(Function<T, U> keyExtractor, Comparator<U> keyComp)

 

studentStream.sorted(Comparator.comparing(Student::getBean) // 반별로 정리

                            .thenComparing(Student::getTotalScore)   // 총점별로 정렬

                            .thenComparing(Student::getName)) // 이름별로 정렬

                            .forEach(System.out::println);

 


실 습 코 드

package Stream;

import java.util.Comparator;
import java.util.stream.Stream;

public class StreamSort {

	public static void main(String[] args) {
		Stream<Student> studentStream = Stream.of(
				new Student("이자바", 3, 300),
				new Student("김자바", 1, 200),
				new Student("안자바", 2, 100),
				new Student("박자바", 2, 150),
				new Student("소자바", 1, 200),
				new Student("나자바", 3, 290),
				new Student("감자바", 3, 180)
				);
		
		studentStream.sorted(Comparator.comparing(Student::getBan)
				.thenComparing(Comparator.naturalOrder()))
				.forEach(System.out::println);
	}

}

class Student implements Comparable<Student>{
	String name;
	int ban;
	int totalScore;
	
	Student(String name,int ban,int totalScore){
		this.name = name;
		this.ban = ban;
		this.totalScore = totalScore;
	}
	
	public String toString() {
		return String.format("[%s, %d, %d]",name, ban, totalScore);
	}

	public String getName() {return name;}
	public int getBan() {return ban;}
	public int getTotalScore() {return totalScore;}

	// 총점 내림차순을 기본 정렬로 한다.
	public int compareTo(Student s) {
		return s.totalScore - this.totalScore;
	}
	
}

Student는 기본 정렬을 Comparable로 구현하고 있고,

Comparable을 구현하면 compareTo 메서드를 오버라이딩 해야함.

그 오버라이딩 부분을 살펴보니 총점 내림차순을 기본 정렬로 한다.

		studentStream.sorted(Comparator.comparing(Student::getBan)
//				.thenComparing(Comparator.naturalOrder()))
				.forEach(System.out::println);

주석 처리하면 기본정렬이 됨.

 

람다식으로 바꾸는 연습

//		studentStream.sorted(Comparator.comparing(Student::getBan)
		studentStream.sorted(Comparator.comparing((Student s) -> s.getBan())
				.thenComparing(Comparator.naturalOrder()))
				.forEach(System.out::println);

 

+ Recent posts