jdk8 functional api

49
JDK8 Functional API Justin Lin [email protected] http://openhome.cc 1

Upload: justin-lin

Post on 08-Sep-2014

6.200 views

Category:

Technology


2 download

DESCRIPTION

These are Java ways of functional style; pragmatic ways of understanding and introducing Lambda/Functional API. 你可以在以下找到中文說明: http://www.codedata.com.tw/java/jdk8-functional-api/

TRANSCRIPT

JDK8 Functional API

Justin Lin

[email protected]

http://openhome.cc

1

Agenda

• Lambda in 10 mins

• Lambda & Refactoring

• Stream...

• Reduction

• Parallelism

• A little Monad

2

Lambda in 10 mins

3

• Anonymous class

• Lambda expressions with no argument

4

• Lambda expressions with arguments

• Type inference

JDK8 built-in functional interface

5

• Target typing

• Method reference

• Default method

6

Lambda & Refactoring

7

• The most beneficial way of using lambdas is introducing them into your existing code base.

8

• Introduce a method.

Finding tracks over one minute

9

Collecting names from each track

10

Filtering tracks over a minute and collecting to a List

Mapping tracks to names and collecting to a Set

11

An Intermediate operation, why don't we chain them together?

Filtering tracks over a minute, mapping tracks to names and collect to a Set

Well, what's stream?

We may just use map(Track::getName)

instead.

12

Stream...

13

• The stream method returns a Stream instance, not a new collection.

• The filter or map method returns a Stream instance, too.

• The collect(toSet()) returns a Set<String> instance as a result.

14

• The Stream instance draw data from the source, could be a collection, an array, a generator function, or an I/O channel. – collection.stream()

– Arrays.stream(array)

– Files.lines(Paths.get(fileName))

– …

• An intermediate operation, such as filter, produces a new Stream instance.

• A terminal operation, such as forEach, produces a non-stream result.

15

• Intermediate operations are lazy…

• You don't have to close streams provided by JDK8 except Files.line, list and walk.

• Compared with the eager way.

16

• Why does Stream's findFirst return Optional?

• Maybe there's no the first one … Why not null?

• Which method of Stream returns Optional? – Optional<T> findAny()

– Optional<T> findFirst()

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

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

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

Null sucks.

Doug Lea

I call it my billion-dollar mistake.

Tony Hoare

17

• Whether an Optional instance containing a value or not is optional, so make appropriate checks to avoid bugs.

• Creating an Optional instance…

– Optional.empty()

– Optional.of(value)

– Optional.ofNullable(value)

• Getting the value orXXX?

– T orElseGet(Supplier<? extends T> other)

– T orElseThrow(Supplier<? extends X> expsp)

18

• Checking by yourself?

• Invoking the specified consumer if a value is present.

• Invoking the specified consumer if the value matches the given predicate.

NoSuchElementException if no value.

19

• Wait! I see wired method signatures in previous examples….Supplier, Consumer, Predicate…What're those types?

• Important functional interfaces used time and time again in JDK8.

Interface Arguments Returns

Consumer<T> T void

Function<T, R> T R

Predicate<T> T boolean

Supplier<T> none T

20

• Consumer<T>

accept T void

21

• Function<T, R>

– Sub interface: UnaryOperator<T>

• Predicate<T>

apply T R

apply T T

test T boolean

Predicate

Function

22

• Supplier<T>

• Fail fast examples if an Optional instance contains no value.

• Avoiding performance overhead.

get none T

NoSuchElementException

23

• To avoid performance overheads, the streams library has primitive versions. They have a clear-cut naming convention.

• Streams for primitives. – IntStream

– LongStream

– DoubleStream

• Functional interfaces for primitives. – XxxConsumer

– XxxPredicate

– XxxSuppiler

– XxxToOooFunction

accept xxx void

test xxx boolean

getAsXxx none xxx

applyAsOoo xxx ooo

24

• Functional interfaces for mapping objects and primitives. – XxxFunction<R>

– ToXxxFunction<T>

• Several functional interfaces starts with Bi-prefix. Take BiConsumer<T, U> for an example.

apply xxx R

applyAsXxx T xxx

accept (T, U) void

25

Reduction

26

• How long of all long tracks?

• Reduce? Sometimes it's called as fold(left).

27

• The max length?

• Reduction operations

– Terminal operations that return one value by reducing the contents of a stream.

– (Reduce, fold or combine, whatever you call it.)

28

• How to reduce the elements of a stream to a more complex object, such as a collection?

• Using collect methods…

29

• The Collectors.toXxx method, such as toSet, doesn't return a Set but a Collector.

• The Collectors provides factory methods for creating out-of-box Collector …

• Grouping …

• Grouping and mapping …

30

• Grouping and reducing …

• Grouping and averaging …

• The stream library picks an appropriate implementation for you.

31

• You might wish to collect your values into a specific Collection.

• Implementing your own Collector…

– supplier、accumulator、combiner、finisher

Creating a new mutable result container

Reducing a value into a mutable result container

Accepting two partial results and merging them

Performing an optional final transform on the container

32

• Implementing your own Collector, a simple example …

33

Parallelism

34

• Concurrency

– Two tasks are making progress at overlapping time periods.

• Parallelism

– Two tasks are happening at literally the same time.

Task 1 Task 2

Core 1

Core 2

Task 1 Task 2

Core 1

Core 2

35

• Changing a single method call…

• Making an operation execute in parallel…

36

• The Java runtime performs a concurrent reduction if … – The stream is parallel. – The Collector has the characteristic Collector.Characteristics.CONCURRENT

– Either the stream is unordered, or the Collector has the characteristic Collector.Characteristics.UNORDERED.

• Built-in concurrent-supported collector – groupingByConcurrent

– toConcurrentMap

37

• Ordering…

• The combining function must be associatve when preforming concurrent reduction…

– 1 + 3 + 8 + 9 + 2 + 5 + 4 + 6 + 7

– (1 + 3) + 8 + (9 + 2) + 5 + (4 + 6 + 7)

– 1 + (3 + 8 )+ 9 + 2 + (5 + 4 + 6 + 7)

38

• Interference

• Performance

– Data size、source data structure、number of cores、cost per element …

• Simply speaking…

– Executing in parallel without worrying about tools doesn't mean there is a free lunch.

Don't do this!! ConcurrentModifiedException

39

A little Monad

40

• Hey, you forget this … why not refactoring it?

• Yes! Coming now … But …

What's flatMap?

41

• The idea of flatMap is from Monad …

• Monad? Let's google it ….

• Great! something can be eaten … XD

42

• A suggestion: getting started from map and flatMap of Optional …

• The map method can change the following …

43

• If your getXXX methods return Optional, you can change the following …

44

Summary • Functional? You've done that when you are …

– Refactoring your existing code …

– Applying filter, map, reduce …

– Returning Optional instead of null …

– Considering issues of parallelism when using parallel tools, such as parallelStream …

– Or even using those monadic API of Java 8 …

• These are Java ways of functional style; pragmatic ways of understanding and introducing Lambda/Functional API

46

Exercise:

– Completing Chapter 1

– Using functional API to refactor Customer again

47

MonsterSupreme

Lambda 就是 重構(重構(程式碼)) Lambda is a way to refactor refactored code

References • http://shop.oreilly.com/product/0636920030713.do • http://www.amazon.com/Refactoring-Improving-

Design-Existing-Code/dp/0201485672 • http://docs.oracle.com/javase/tutorial/collections/stre

ams/index.html • http://docs.oracle.com/javase/tutorial/collections/stre

ams/reduction.html • http://openhome.cc/Gossip/Java/FlatMap.html • http://www.codedata.com.tw/java/jdk8-

completablefuture/ • http://www.slideshare.net/mariofusco/monadic-java

48

Thanks!!

Justin Lin

[email protected]

http://openhome.cc

49