Understand Java’s Key Functional Programming Concepts & Features Douglas C. Schmidt d[email protected] www.dre.vanderbilt.edu/~schmidt
Professor of Computer Science Institute for Software Integrated Systems Vanderbilt University Nashville, Tennessee, USA Learning Objectives in this Lesson • Understand key functional programming concepts & features supported by Java
These functional programming features2 were added in Java 8 & expanded later Learning Objectives in this Lesson • Understand key functional programming concepts & features supported by Java • Know how to compare & contrast functional programming & object-oriented programming
3 Key Functional Programming Concepts in Java
4 Key Functional Programming Concepts in Java • Functional programming has its roots in lambda calculus
See en.wikipedia.org/wiki/5 Functional_programming Key Functional Programming Concepts in Java • Functional programming has its roots Input x in lambda calculus, e.g., • Computations are treated as Function f evaluation of math functions Output f(x)
Ideally, each function is “pure,” i.e., it has no side- effects on memory or I/O
See en.wikipedia.org/wiki/Functional_programming#Pure_functions6 Key Functional Programming Concepts in Java • Functional programming has its roots Input x in lambda calculus, e.g., • Computations are treated as Function f evaluation of math functions Output f(x)
Function g Output g(f(x)) Note “function composition”: the output of one function serves as Function h the input to the next function, etc. Output h(g(f(x)))
See martinfowler.com/articles/collection7 -pipeline Key Functional Programming Concepts in Java • Functional programming has its roots Input x in lambda calculus, e.g., • Computations are treated as Function f evaluation of math functions Output f(x) Functionally compute the ‘nth’ factorial in parallel long factorial Function g (long n) { return LongStream Output g(f(x)) .rangeClosed(1, n) .parallel() Function h .reduce(1, (a, b) -> a * b); Output h(g(f(x))) }
See github.com/douglascraigschmidt8/LiveLessons/tree/master/Java8/ex16 Key Functional Programming Concepts in Java • Functional programming has its roots Range of longs from 1..8 in lambda calculus, e.g.,
• Computations are treated as longs 1..4 longs 5..8 evaluation of math functions
longs 1..2 longs 3..4 longs 5..6 longs 7..8 long factorial (long n) { return LongStream .rangeClosed(1, n) Generate a stream of longs from .parallel() 1 to n in parallel (where n == 8) .reduce(1, (a, b) -> a * b); }
See www.baeldung.com/java9 -8-streams Key Functional Programming Concepts in Java • Functional programming has its roots Range of longs from 1..8 in lambda calculus, e.g.,
• Computations are treated as longs 1..4 longs 5..8 evaluation of math functions
longs 1..2 longs 3..4 longs 5..6 longs 7..8 long factorial (long n) { Process Process Process Process sequentially sequentially sequentially sequentially return LongStream .rangeClosed(1, n) 2 12 30 56 .parallel() .reduce(1, (a, b) -> a * b); Multiply pair-wise values in parallel }
See docs.oracle.com/javase/tutorial/collections/streams/parallelism.html10 Key Functional Programming Concepts in Java • Functional programming has its roots Range of longs from 1..8 in lambda calculus, e.g.,
• Computations are treated as longs 1..4 longs 5..8 evaluation of math functions
longs 1..2 longs 3..4 longs 5..6 longs 7..8 long factorial (long n) { Process Process Process Process sequentially sequentially sequentially sequentially return LongStream .rangeClosed(1, n) 2 12 30 56 .parallel() .reduce(1, 24 reduce() reduce() 1,680 (a, b) -> a * b); reduce() } 40,320
Successively combine two immutable11 long values & produce a new one Key Functional Programming Concepts in Java • Functional programming has its roots in lambda calculus, e.g., • Computations are treated as evaluation of math functions • Changing state & mutable shared data are discouraged to avoid various hazards
See en.wikipedia.org/wiki/Side_effect12 _(computer_science) Key Functional Programming Concepts in Java • Functional programming has its roots class Total { in lambda calculus, e.g., public long mTotal = 1; • Computations are treated as public void mult(long n) evaluation of math functions { mTotal *= n; } • Changing state & mutable shared data } are discouraged to avoid various hazards long factorial(long n) { Total t = new Total(); LongStream.rangeClosed(1, n) .parallel() .forEach(t::mult); return t.mTotal; }
See github.com/douglascraigschmidt13/LiveLessons/tree/master/Java8/ex16 Key Functional Programming Concepts in Java • Functional programming has its roots class Total { in lambda calculus, e.g., public long mTotal = 1; • Computations are treated as public void mult(long n) evaluation of math functions { mTotal *= n; } • Changing state & mutable shared data } are discouraged to avoid various hazards Shared mutable state long factorial(long n) { Total t = new Total(); LongStream.rangeClosed(1, n) .parallel() .forEach(t::mult); return t.mTotal; }
See github.com/douglascraigschmidt14/LiveLessons/tree/master/Java8/ex16 Key Functional Programming Concepts in Java • Functional programming has its roots class Total { in lambda calculus, e.g., public long mTotal = 1; • Computations are treated as public void mult(long n) evaluation of math functions { mTotal *= n; } • Changing state & mutable shared data } are discouraged to avoid various hazards long factorial(long n) { Total t = new Total(); rangeClosed() LongStream.rangeClosed(1, n) .parallel() Run in parallel parallel() .forEach(t::mult); return t.mTotal; } forEach()
See docs.oracle.com/javase/tutorial/collections/streams/parallelism.html15 Key Functional Programming Concepts in Java • Functional programming has its roots class Total { in lambda calculus, e.g., public long mTotal = 1; • Computations are treated as public void mult(long n) evaluation of math functions { mTotal *= n; } • Changing state & mutable shared data } are discouraged to avoid various hazards Beware of race conditions!!! long factorial(long n) { Total t = new Total(); LongStream.rangeClosed(1, n) .parallel() .forEach(t::mult); return t.mTotal; }
See en.wikipedia.org/wiki/16Race_condition#Software Key Functional Programming Concepts in Java • Functional programming has its roots class Total { in lambda calculus, e.g., public long mTotal = 1; • Computations are treated as public void mult(long n) evaluation of math functions { mTotal *= n; } • Changing state & mutable shared data } are discouraged to avoid various hazards long factorial(long n) { Total t = new Total(); LongStream.rangeClosed(1, n) .parallel() .forEach(t::mult); return t.mTotal; } Beware of inconsistent memory visibility See jeremymanson.blogspot.com/2007/08/atomicity17 -visibility-and-ordering.html Key Functional Programming Concepts in Java • Functional programming has its roots class Total { in lambda calculus, e.g., public long mTotal = 1; • Computations are treated as public void mult(long n) evaluation of math functions { mTotal *= n; } • Changing state & mutable shared data } are discouraged to avoid various hazards long factorial(long n) { Total t = new Total(); LongStream.rangeClosed(1, n) .parallel() .forEach(t::mult); return t.mTotal; Only you can prevent } concurrency hazards!
In Java you must avoid these hazards, 18i.e., the compiler & JVM won’t save you.. Key Functional Programming Concepts in Java • Functional programming has its roots in lambda calculus, e.g., • Computations are treated as evaluation of math functions • Changing state & mutable shared data are discouraged to avoid various hazards • Instead, focus is on “immutable” objects
See docs.oracle.com/javase/tutorial/essential/concurrency/immutable.html19 Key Functional Programming Concepts in Java • Functional programming has its roots final class String { in lambda calculus, e.g., private final char value[]; ... • Computations are treated as evaluation of math functions public String(String s) { • Changing state & mutable shared data value = s; are discouraged to avoid various hazards ... } • Instead, focus is on “immutable” objects • Immutable object state cannot public int length() { return value.length; change after it is constructed } ... }
See www.baeldung.com/java20 -immutable-object Key Functional Programming Concepts in Java • Functional programming has its roots final class String { in lambda calculus, e.g., private final char value[]; ... • Computations are treated as evaluation of math functions public String(String s) { • Changing state & mutable shared data value = s; are discouraged to avoid various hazards ... } • Instead, focus is on “immutable” objects • Immutable object state cannot public int length() { return value.length; change after it is constructed } • Java String is a common example ... of an immutable object }
See docs.oracle.com/javase/8/docs/21 api/java/lang/String.html Key Functional Programming Concepts in Java • Functional programming has its roots final class String { in lambda calculus, e.g., private final char value[]; ... • Computations are treated as evaluation of math functions public String(String s) { • Changing state & mutable shared data value = s; are discouraged to avoid various hazards ... } • Instead, focus is on “immutable” objects • Immutable object state cannot public int length() { return value.length; change after it is constructed } • Java String is a common example ... of an immutable object } • Fields are final & only accessor methods
See www.programcreek.com/2013/04/why22 -string-is-immutable-in-java Functional vs. Object-Oriented Programming in Java
23 Functional vs. Object-Oriented Programming in Java • In contrast to functional programming, OO programming employs “hierarchical data abstraction”
See en.wikipedia.org/wiki/Object24 -oriented_design Functional vs. Object-Oriented Programming in Java • In contrast to functional programming, OO programming employs “hierarchical data abstraction”, e.g. • Components are based on stable class roles & relationships extensible via inheritance & dynamic binding
See en.wikipedia.org/wiki/Object25 -oriented_programming Functional vs. Object-Oriented Programming in Java • In contrast to functional programming, OO programming employs “hierarchical data abstraction”, e.g. • Components are based on stable class roles & relationships extensible via inheritance & dynamic binding • Rather than algorithmic actions implemented as functions
See www.drdobbs.com/windows/software26-complexity-bringing-order-to-ch/199901062 Functional vs. Object-Oriented Programming in Java • In contrast to functional programming, OO Tree tree = ...; programming employs “hierarchical data Visitor printVisitor = abstraction”, e.g. makeVisitor(...); • Components are based on stable class for(Iterator
See en.wikipedia.org/wiki/27Imperative_programming Functional vs. Object-Oriented Programming in Java • In contrast to functional programming, OO Tree tree = ...; programming employs “hierarchical data Visitor printVisitor = abstraction”, e.g. makeVisitor(...); • Components are based on stable class for(Iterator
Access & update internal iterator state
State is often “mutable”28 in OO programs End of Understand Java’s Key Functional Programming Concepts & Features
29