The parallel streams promise
Java 8 sold free parallelism. Here is when the promise holds and when it costs you.
Open this lesson in the learning hubKey points
- Adding
.parallel()really does split the work across the common ForkJoinPool. - It pays off when the data is large, splitting is cheap, and the work per element is CPU-bound.
- It loses when the source splits badly (
LinkedList), the work is tiny, or you block on I/O. - The common pool is shared by the whole JVM - one blocking parallel stream stalls unrelated code.
- Order-sensitive operations pay extra to preserve encounter order, which can erase the gain entirely.
Example
import java.util.*;
import java.util.stream.*;
public class Main {
public static void main(String[] args) {
List<Integer> data = IntStream.rangeClosed(1, 2_000_00).boxed().collect(Collectors.toList());
long t1 = System.nanoTime();
long seq = data.stream().mapToLong(Main::work).sum();
long seqMs = (System.nanoTime() - t1) / 1_000_000;
long t2 = System.nanoTime();
long par = data.parallelStream().mapToLong(Main::work).sum();
long parMs = (System.nanoTime() - t2) / 1_000_000;
System.out.println("sequential : " + seq + " (" + seqMs + " ms)");
System.out.println("parallel : " + par + " (" + parMs + " ms)");
System.out.println("same answer: " + (seq == par));
System.out.println("cores : " + Runtime.getRuntime().availableProcessors());
System.out.println("(timings vary; on a small input parallel is often slower)");
}
static long work(int n) {
return (long) Math.sqrt(n) + (n % 7);
}
}
Parallel is a measurement, not a decision - if you have not timed it, leave it sequential.
This is a reading copy. The full lesson — with the visual explainer, the interactive lab and a Run button for the code — lives in the Java 8 Course course, and every lesson in it is listed on the Java 8 Course contents page.