자바 8 스트림 API

26
Java 8 Stream API A different way to process collections 09:18:24

description

Java 8 Steam API

Transcript of 자바 8 스트림 API

Page 1: 자바 8 스트림 API

Java 8 Stream APIA different way to process collections

09:18:24

Page 2: 자바 8 스트림 API

09:19:27

HTTP://starplatina.tistory.com

[email protected]

@sleepJune

김제준

Page 3: 자바 8 스트림 API

나즈혼

람다기본메서드

STREAM API날짜 API

동시성 개선

Base 64

메타프로그래밍 향상

자바스크립트 엔진

2014.3 현재 버전 8.25

09:18:25

Page 4: 자바 8 스트림 API

List transactionIds = new ArrayList(); for (Transaction t : groceryTransactions) {

transactionIds.add(t.getId()); }

Collections.sort(groceryTransactions, new Comparator() { public int compare(Transaction t1, Transaction t2) {

return t2.getValue().compareTo(t1.getValue()); }

});

List groceryTransactions = new ArrayList(); for (Transaction t : groceryTransactions) {

if (t.getType() == Transaction.GROCERY) { groceryTransactions.add(t);

} }

Java 코드로 구매내역 구하기

식료품점에서 구매한걸 찾고

사용 금액 순으로 정렬한 뒤

거래 내역의 ID를 추출

09:18:25

Page 5: 자바 8 스트림 API

그럼 Database에서는?

SELECT id FROM TRANSACTIONSWHERE type = ‘GROCERY’ ORDER BY value DESC

별도의 작업 없이 이미 등록된 집계 함수를 사용

SUM, MAX, COUNT, AVG 등등

09:18:25

Page 6: 자바 8 스트림 API

List groceryTransactions = new ArrayList(); for (Transaction t : groceryTransactions) {

if (t.getType() == Transaction.GROCERY) { groceryTransactions.add(t);

} }

Collections.sort(groceryTransactions, new Comparator() { public int compare(Transaction t1, Transaction t2) {

return t2.getValue().compareTo(t1.getValue()); }

});

List transactionIds = new ArrayList(); for (Transaction t : groceryTransactions) {

transactionIds.add(t.getId()); }

다시 한번 자바 코드

길다!

복잡하다!

코딩해야된다!09:18:25

Page 7: 자바 8 스트림 API

그래서 준비 했습니다!

List transactionsIds = transactions.stream()

.filter(t -> t.getType() == Transaction.GROCERY)

.sorted(Comparator.comparing(Transaction::getValue).reversed())

.map(Transaction::getId)

.collect(Collectors.toList());

람다 표현식

메소드 참조

09:18:25

Page 8: 자바 8 스트림 API

일반적인 스트림의 흐름

filter sorted map collecttransactions

2. 중간 작업 (Intermediate Operations)

PipeLine1. 데이터소스

3. 종료 작업 (Terminal Operations)

09:18:25

Page 9: 자바 8 스트림 API

중간 작업 및 종료 작업

중간 작업(Intermediate Operations)

• 항상 스트림을 리턴• Pipeline 형태로 연결 시킬 수 잇음• 데이터를 처리하기 위한 로직• 직접 처리를 시작 할 수는 없음

• 오브젝트를 리턴 하거나, collection 또는 void 리턴 가능• Pipeline으로 구성된 작업을 시작• 한번 수행되고 난 후에 작업한 스트림에 재작업 불가능

종료 작업(Terminal Operations)

flatMap

map

distinct

sorted

limitpeek

filterforeach

skip

toArray

reduce

collect

minmaxcount

anyMatchallMatchnoneMatchfirstFind

anyFind

09:18:25

Page 10: 자바 8 스트림 API

좀 더 상세히Id : 1

Value : 100Id : 3

Value : 80Id : 6

Value : 120Id : 10

Value : 50Id : 7

Value : 40Stream <Transaction)

Id : 3Value : 80

Id : 6Value : 120

Id : 10Value : 50

.filter(t -> t.getType() == Transaction.GROCERY)

Stream <Transaction)

Id : 6Value : 120

Id : 3Value : 80

Id : 10Value : 50

.sorted(Comparator.comparing(Transaction::getValue).reversed())

Stream <Transaction)

6 3 10.map(Transaction::getId) Stream <Integer)

6 3 10

.collect(Collectors.toList()); List<Integer)

09:18:25

Page 11: 자바 8 스트림 API

Stream API• Java.util.stream• 연산의 선언적 서술

• 반복 구조 캡슐화, 알고리듬 분리• 제어 흐름 추상화

• 함수형 방식 처리 : 데이터 불변• 지연 처리, 대부분의 작업을 단일 반복 수행으로 처리• 무한 연속 데이터 흐름 API• 다양한 데이터 원천 지원: 컬렉션, 생성 메서드, 파일 I/O 등

09:18:25

Page 12: 자바 8 스트림 API

컬렉션과 스트림

스트림

컬렉션

List Map Set

보관형 자료구조

데이터 처리 추상화

09:18:25

Page 13: 자바 8 스트림 API

스트림과 컬렉션 처리 방법의 차이

• 파이프라이닝(Pipelining)• 많은 스트림의 기능들이 스트림 자기 자신을 리턴• 처리 작업이 체인처럼 연결되어 큰 파이프라인처럼 동작 하도록 함

• 내부 반복(Internal Iteration)• 명시적으로 반복작업을 수행해야되는 컬렉션과 달리 스트림 작업은 내부에서 처리

09:18:25

Page 14: 자바 8 스트림 API

잠시 중간 정리

1. 질의를 할 데이터소스(Collection 같은)가 필요2. 파이프라인을 형성하는 중간 작업(Intermediate Operations)3. 파이프라인을 실행하고 결과를 리턴하는 종료 작업(Terminal

Operations)

Stream 을 사용하는 일반적인 3가지 내용

09:18:25

Page 15: 자바 8 스트림 API

java.util.stream

• Building Streams• Infinite Streams• Numeric Streams• Filtering• Mapping• Finding and matching• Reducing• Collect

09:18:25

Page 16: 자바 8 스트림 API

Building Streams

Stream<Integer> numbersFromValues = Stream.of(1, 2, 3, 4); int[] numbers = {1, 2, 3, 4};

IntStream numbersFromArray = Arrays.stream(numbers);

long numberOfLines = Files.lines(

Paths.get(“yourFile.txt”), Charset.defaultCharset()).count();

Collection, 숫자들, 값 목록, 배열, 파일

값 목록, 배열에서 Stream 생성

파일에서 Stream 생성

09:18:25

Page 17: 자바 8 스트림 API

Infinite StreamsStream<Integer> numbers = Stream.iterate(0, n -> n + 10);

numbers.limit(5).forEach(System.out::println); // 0, 10, 20, 30, 40

Stream.iterate

Stream.generate

09:18:25

Page 18: 자바 8 스트림 API

Numeric Streamsint statement = transactions.stream()

.map(Transaction::getValue)

.sum(); // error since Stream has no sum method

int statementSum = transactions.stream()

.mapToInt(Transaction::getValue)

.sum(); // works!

IntStreamDoubleStreamLongStream

mapToIntmapToDoublemapToLong

sum(), min(), max(), average(), count()

int statementSum = transactions.stream() .mapToInt(Transaction::getValue)

.IntSummaryStatistics();

// IntSummaryStatistics{count=7, sum=28, min=1, average=4.000000, max=7}

09:18:25

Page 19: 자바 8 스트림 API

Filtering

• filter • 주어진 predicate와 일치하는 stream을 리턴

• distinct• 중복을 제거한 유니크 엘리먼트 stream을 리턴

• limit(n)• 주어진 사이즈(n) 까지의 stream을 리턴

• skip(n)• 주어진 엘리먼트 길이 까지 제외한 stream을 리턴

09:18:25

Page 20: 자바 8 스트림 API

MappingList<String> words = Arrays.asList("Oracle", "Java", "Magazine"); List<Integer> wordLengths = words.stream()

.map(String::length)

.collect(toList());

map(String::length) 인자로 전달 받은 값들을 가지고 새로운 Stream 생성

List에 저장된 단어들의 길이를 가지고 있는 새로운 list 생성

map(e -> e * 2) map(s -> s.toUpperCase())

09:18:25

Page 21: 자바 8 스트림 API

Finding and Matching

transactions.stream() .filter(t -> t.getType() == Transaction.GROCERY) .findAny()

.ifPresent(System.out::println);

boolean expensive = transactions.stream()

.allMatch(t -> t.getValue() > 100);

anyMatch, allMatch, noneMatch

Optional<Transaction> = transactions.stream().filter(t -> t.getType() == Transaction.GROCERY)

.findAny();

findFirst, findAny

java.util.Optional

09:18:25

Page 22: 자바 8 스트림 API

Reducingint sum = 0; for (int x : numbers) { sum += x; }

int sum = numbers.stream().reduce(0, (a, b) -> a + b);

int product = numbers.stream().reduce(1, (a, b) -> a * b);

int product = numbers.stream().reduce(1, Integer::max);

for loop 를 활용한 덧셈

초기화 값 : 0BinaryOperator<T> : 두개의 엘리멘트를 더해 새로운 값을 생성

모든 값을 곱하기

최대값 구하기

엘리먼트들을 하나의 결과로 추출

09:18:25

Page 23: 자바 8 스트림 API

Collect

09:18:25

List<Person> filtered = persons .stream() .filter(p -> p.name.startsWith("P"))

.collect(Collectors.toList()); // Collectors.toSet()

System.out.println(filtered); // [Peter, Pamela]

Map<Integer, List<Person>> personsByAge = persons .stream()

.collect(Collectors.groupingBy(p -> p.age));

personsByAge .forEach((age, p) -> System.out.format("age %s: %s\n", age, p));

// age 18: [Max] // age 23: [Peter, Pamela] // age 12: [David]

Page 24: 자바 8 스트림 API

정리1.Stream API 의 다양한 기능을 활용해 데이터 처리를 최적화 할 수 있다.2.람다와 메서드 참조를 알아 두면 더 좋음!3.병렬 처리를 손쉽게 지원

• stream() -> parallelStream()

09:18:25

Page 25: 자바 8 스트림 API

참고자료1. Processing Data with Java SE 8 Streams

• http://www.oracle.com/technetwork/articles/java/ma14-java-se-8-streams-2177646.html

2. Beyond Java : 자바 8을 중심으로 본 자바의 혁신• http://www.slideshare.net/gyumee/beyond-java-8

3. java.util.stream• https://docs.oracle.com/javase/8/docs/api/java/util/stream/package-summary.html

Page 26: 자바 8 스트림 API

THANK YOU!

09:18:25