Hello

JAVA Stream 본문

try

JAVA Stream

nari0_0 2019. 10. 1. 08:02
728x90

람다식(lambda expressions) ==익명함수==일급객체

메서드의 이름과 반환값이 없는 하나의 식으로 표현한다. 이것은 함수를 간략하고 명확하게 표현할 수 있도록 한다.

 

메서드와 함수의 차이는 메서드는 객체의 동작 행위를 의미하고 틀정 클래스에 반드시 속해있어야합니다.

함수는 같지만 객체(클래스)에 속하지 않고 독립적으로 기능을 동작할 수 있는 것을 의미합니다. 람다식은 메서드가 하나의 독립적인 기능을 하기 때문에 함수라고 불릴 수 있습니다.

 

기본 식  () -> {}

 

람다식을 사용하기 위한 인터페이스를 함수형 인터페이스로 말하며, 이는 익명 클래스의 객체와 동등합니다. 

함수형 인터페이스는 람다식과 인터페이스의 메서드가 단일로 연결되기 위해 추상메서드가 하나만 정의되어 있어합니다. static, default method는 함수형 인터페이스 내에서 자유롭게 작성할 수 있습니다.

-일급객체는 다른 객체들에 적용 가능한 연산을 모두 지원하는 개체를 말합니다. 그리고 변수를 담고 인자로 전달 하고 반환값으로 전달 할 수 있어야 람다는 이것이 가능하기 때문에 일급객체라고 불릴 수 있습니다.

함수를 값으로 사용 할 수도 있으며 파라메터로 전달 및 변수에 대입 하기와 같은 연산들이 가능합니다.

interface A {
     abstract int add(int a);
}

A a = new A() {
     public int add(int a) {
          return a + 10;
}
};


A aa = (b)->b+100;

익명클래스를 사용하는 방법을 람다식으로 표현하면 좀더 간결하고 명확하게 작성한 것을 알 수 있습니다.

 

 

스트림은 컬랙션과 배열의 요소를 for를 사용해 요소를 하나씩 다루는 기존의 방식에서 람다식을 적용하여 함수형으로 요소를 가공하고 결과를 얻을 수 있습니다. 그리고 직접 스레드 코드를 구현하지 않고 간단하게 병렬처리가 가능합니다.

 

데이터 소스를 추상화하여 이 것에 구애받지 않고 같은 방식으로 다룰 수 있게 한것이다.스트림은 컬랙션 배열 등 다양한 데이터 소스에서 생성이 가능합니다.

 

스트림은 일회용으로 사용되기 때문에 최종연산이 된 후에 해당 스트림을 재사용 할 수 없습니다. 필요하다면 기존의 데이터 소스를 스트림으로 생성해서 사용해야 합니다.

 

스트림의 연산은 중간연산과, 최종연산으로 분류할 수 합니다.

중간연산은 연산 후 스트림을 반환해 다른 중간연산을 연결해서 사용이 가능하고 최종연산은 스트림을 소모하여 한번만 연산합니다. 즉, 중간연산은 스트림을 변환하는데 최종연산은 스트림을 소비(사용)하는데 목적을 가집니다.

연산을 연결하는 것을 파이프라인이라고 말하고 builder pattern과 비슷하다고 생각하면 된다.

 

String[] strs =  {"bad","liar","imagine","dragons","bad"};

filter() 각각 주어진 조건에 맞는 요소만 구성된 스트림을 반환합니다.

distinct() 메소드 내부의 equals() 메소드를 사용해 중복을 비교하고 제거된 스트림을 반환합니다.

Arrays.stream(strs)
     .filter(x->x.indexOf("i")<0)  --문자열에서 i가 들어가지 않은 문자 필터링 ("bad","dragons","bad")
     .distinct()  --중복 문자 제거 ('bad')
     .forEach(System.out::println); bad, dragons 를 출력

map() 스트림 요소를 함수의 인수로 전달해 그반환값으로 새로운 스트림을 반환합니다.

Arrays.stream(strs)
     .map(x->x.concat("add"))
     .forEach(System.out::println);

flatMap() 해당 스트림의 요소가 배열로 한번 더 감싸져 있다면 배열의 요소를 반환해 하나로 합친 스트림을 반환합니다.

String[][] strs =  {{"liar","imagine"},{"dragons","bad"}};

System.out.println(strs); --주소값이 나온다

Arrays.stream(strs)
     .flatMap(Arrays::stream) --요소를 스트림 형태에서 Arrays로 값을 변환
     .forEach(System.out::println); --요소 값이 나온다.

 

최종연산

allMatch, anyMatch, noneMatch 각각 모든 요소가 일치하는지, 하나라도 일치하는지, 하나도 일지하지 않는지 boolean 으로 return 됨.

collect는 stream을 다른 형식으로 변환해 return 한다.

- toList()를 가장 많이 사용하며 요소들을 list형태로 반환

List list = Arrays.stream(strs)
     .flatMap(Arrays::stream)
     .collect(Collectors.toList());

- groupingBy()는 sql의 group by와 유사하게 동작하며 기준에 맞춰 grouping된 결과를 반환

 

 

728x90

'try' 카테고리의 다른 글

spring boot에 swagger2 적용  (0) 2020.01.29
Java Generic  (0) 2019.09.18
객체와 객체지향 프로그래밍  (0) 2019.09.10
2019.09.03  (0) 2019.09.03
2019.09.01  (0) 2019.09.01