java 8 parallel imagestreamgang example (part 3)schmidt/cs891f/2018-pdfs/18-java... ·...

35
Java 8 Parallel ImageStreamGang Example (Part 3) Douglas C. Schmidt [email protected] www.dre.vanderbilt.edu/~schmidt Professor of Computer Science Institute for Software Integrated Systems Vanderbilt University Nashville, Tennessee, USA

Upload: others

Post on 06-Aug-2020

22 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

Java 8 Parallel ImageStreamGang

Example (Part 3)

Douglas C. [email protected]

www.dre.vanderbilt.edu/~schmidt

Professor of Computer Science

Institute for Software

Integrated Systems

Vanderbilt University

Nashville, Tennessee, USA

Page 2: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

2

Learning Objectives in this Part of the Lesson• Recognize the structure/functionality

of the ImageStreamGang app

• Know how Java 8 parallel streams areapplied to the ImageStreamGang app

• Understand the parallel streams implementation of ImageStreamGang

See github.com/douglascraigschmidt/LiveLessons/blob/master/ImageStreamGang

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages =

urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

Page 3: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

3

Learning Objectives in this Part of the Lesson• Recognize the structure/functionality

of the ImageStreamGang app

• Know how Java 8 parallel streams areapplied to the ImageStreamGang app

• Understand the parallel streams implementation of ImageStreamGang

• Be aware of the pros & cons of the parallel streams solution

See github.com/douglascraigschmidt/LiveLessons/blob/master/ImageStreamGang

Page 4: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

4

Implementing a Parallel Stream in ImageStreamGang

Page 5: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

5

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

See imagestreamgang/streams/ImageStreamParallel.java

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

Page 6: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

6

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

Get a list of URLs

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

getInput() is defined by the underlying StreamGang framework

Page 7: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

7

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

Convert a collection into a parallel stream

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

Page 8: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

8

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

Return an output stream consisting of the URLs in the input stream that are

not already cached

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

See docs.oracle.com/javase/8/docs/api/java/util/stream/Stream.html#filter

Page 9: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

9

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

Return an output stream consisting of the URLs in the input stream that are

not already cached

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

# of output stream elements will be <= # of input stream elements

Page 10: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

10

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

boolean urlCached(URL url) {

return mFilters

.stream()

.filter(filter ->

urlCached(url,

filter.getName()))

.count() > 0;

}

See imagestreamgang/streams/ImageStreamGang.java

Determine whether this url has been downloaded to an image & had filters applied to it yet

Page 11: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

11

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

boolean urlCached(URL url,

String filterName) {

File file =

new File(getPath(),

filterName);

File imageFile =

new File(file,

getNameForUrl(url));

return imageFile.exists();

}

See imagestreamgang/streams/ImageStreamGang.java

Check if a file with this name already exists

Page 12: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

12

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

See imagestreamgang/streams/ImageStreamGang.javaThere are clearly better ways of implementing an image cache!

Page 13: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

13

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

Return an output stream consisting of the images that were downloaded from the URLs in the input stream

See docs.oracle.com/javase/8/docs/api/java/util/stream/Stream.html#map

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

Page 14: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

14

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

# of output stream elements must match the # of input stream elements

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

Return an output stream consisting of the images that were downloaded from the URLs in the input stream

Page 15: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

15See imagestreamgang/streams/ImageStreamParallel.java

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

Image blockingDownload

(URL url) {

return BlockingTask

.callInManagedBlocker

(() ->

downloadImage(url));

}

Downloads content from a url& converts it into an image

Page 16: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

16

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

Image blockingDownload

(URL url) {

return BlockingTask

.callInManagedBlocker

(() ->

downloadImage(url));

}

We covered BlockingTask.callInManagedBlocker() earlier in this course

Uses a “managed blocker” to ensure sufficient threads are in

the common fork-join pool

Page 17: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

17

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

Image blockingDownload

(URL url) {

return BlockingTask

.callInManagedBlocker

(() ->

downloadImage(url));

}

See www.ibm.com/developerworks/library/j-jtp0730

I/O-bound tasks on an N-core CPU typically run best with

N*(1+WT/ST) threads (WT = wait time & ST = service time)

Page 18: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

18

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

Return an output stream containing the results of applying a list of filters to each image in the input stream & storing the results in the file system

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

See docs.oracle.com/javase/8/docs/api/java/util/stream/Stream.html#flatMap

Page 19: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

19

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

# of output stream elements may differ from the # of input stream elements

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

Return an output stream containing the results of applying a list of filters to each image in the input stream & storing the results in the file system

Page 20: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

20

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

Stream<Image> applyFilters

(Image image) {

return mFilters

.parallelStream()

.map(filter ->

makeFilterWithImage

(filter,

image).run())

}

See imagestreamgang/streams/ImageStreamParallel.java

Apply all filters to an image in parallel & store on the device

Page 21: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

21

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

collect() is a “reduction” operation that combines elements into one result

See docs.oracle.com/javase/8/docs/api/java/util/stream/Stream.html#collect

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

Page 22: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

22

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

Trigger all intermediate operations

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

Page 23: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

23

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

Create a list containing all the filtered & stored images

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

Page 24: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

24

Implementing a Parallel Stream in ImageStreamGang• We focus on processStream()

in ImageStreamParallel.java

Logs the # of images that were downloaded, filtered, & stored

void processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

Page 25: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

25

Pros of the Java 8 Parallel Streams Solution

Page 26: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

26

Pros of the Java 8 Parallel Streams Solution• The parallel stream version is faster than the sequential streams version

ImageStreamGang

Starting ImageStreamGangTestPrinting results for input 1 from fastest to slowestCOMPLETABLE_FUTURES_2 executed in 276 msecsCOMPLETABLE_FUTURES_1 executed in 285 msecsPARALLEL_STREAM executed in 383 msecsSEQUENTIAL_STREAM executed in 1288 msecs

Printing results for input 2 from fastest to slowestCOMPLETABLE_FUTURES_1 executed in 137 msecsCOMPLETABLE_FUTURES_2 executed in 138 msecsPARALLEL_STREAM executed in 170 msecsSEQUENTIAL_STREAM executed in 393 msecsEnding ImageStreamGangTest

The performance speedup isn’t quite linear on my quad-core computer

Page 27: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

27

Pros of the Java 8 Parallel Streams Solution• The parallel stream version is faster than the sequential streams version

• e.g., images are downloaded & processedin parallel on multiple cores

Page 28: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

28

Pros of the Java 8 Parallel Streams Solutionvoid processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

• The solution is relatively straight forward to understand

Page 29: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

29

Pros of the Java 8 Parallel Streams Solutionvoid processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

• The solution is relatively straight forward to understand, e.g.

• The behaviors map cleanly onto the design intent

Page 30: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

30

Pros of the Java 8 Parallel Streams Solutionvoid processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

• The solution is relatively straight forward to understand, e.g.

• The behaviors map cleanly onto the design intent

• Behaviors are all synchronous

CALLER CALLEE

Check the cache

Download the image

return result

return result

Page 31: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

31

Pros of the Java 8 Parallel Streams Solutionvoid processStream() {

List<URL> urls = getInput();

List<Image> filteredImages = urls

.parallelStream()

.filter(not(this::urlCached))

.map(this::blockingDownload)

.flatMap(this::applyFilters)

.collect(toList());

System.out.println(TAG

+ "Image(s) filtered = "

+ filteredImages.size());

}

• The solution is relatively straight forward to understand, e.g.

• The behaviors map cleanly onto the design intent

• Behaviors are all synchronous

• The flow of control can beread “linearly”

Page 32: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

32

Cons of the Java 8 Parallel Streams Solution

Page 33: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

33

Cons of the Java 8 Parallel Streams Solution• The completable futures versions are faster than the parallel streams version

ImageStreamGang

Starting ImageStreamGangTestPrinting results for input 1 from fastest to slowestCOMPLETABLE_FUTURES_2 executed in 276 msecsCOMPLETABLE_FUTURES_1 executed in 285 msecsPARALLEL_STREAM executed in 383 msecsSEQUENTIAL_STREAM executed in 1288 msecs

Printing results for input 2 from fastest to slowestCOMPLETABLE_FUTURES_1 executed in 137 msecsCOMPLETABLE_FUTURES_2 executed in 138 msecsPARALLEL_STREAM executed in 170 msecsSEQUENTIAL_STREAM executed in 393 msecsEnding ImageStreamGangTest

Page 34: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

34

• In general, there's a tradeoff between computing performance & programmer productivity when choosing amongst Java 8 parallelism frameworks

• i.e., completable futures are more efficient & scalable than parallel streams, but are somewhat harder to program

Performance

Productivity

Cons of the Java 8 Parallel Streams Solution

Page 35: Java 8 Parallel ImageStreamGang Example (Part 3)schmidt/cs891f/2018-PDFs/18-Java... · 2018-10-24 · 8 Implementing a Parallel Stream in ImageStreamGang •We focus on processStream()

35

End of Java 8 Parallel ImageStreamGang Example

(Part 3)