Interview replay
Full round replay — parallel streams
Timed verbal replay with pass/fail criteria per follow-up.
How to run this
The opener
“When is parallelStream() a mistake?”
Budget: 45 seconds. Going long here is itself a fail signal.
Follow-ups
1. “Which pool does it use?”
Testing: The single fact the whole topic rests on.
Scoring
Pass: The common ForkJoinPool — a JVM-wide singleton with parallelism of availableProcessors minus one. You did not create it and you do not own it.
Fail: Says it creates threads, or that you configure the pool per stream.
2. “Is parallelStream asynchronous?”
Testing: A very common assumption.
Scoring
Pass: No. The calling thread joins the work and blocks until the whole pipeline finishes — it is one of the workers, which you can see by printing thread names.
Fail: Treats it as fire-and-forget.
3. “Why is a slow remote call inside one a problem beyond being slow?”
Testing: Do they reach the JVM-wide consequence?
Scoring
Pass: It occupies common-pool workers, so every other parallel stream in the process — including inside libraries — queues behind it. Benchmarking the code in isolation never shows it.
Fail: Only says the stream itself will be slow.
4. “How do you give a parallel stream its own pool?”
Testing: And whether they know it is not an API.
Scoring
Pass: Evaluate it inside a task submitted to your own ForkJoinPool; the stream uses the pool of the task it runs in. There is no overload taking a pool, so it is a documented behaviour rather than an API — and often a sign an ExecutorService fits better.
Fail: Believes there is a parallelStream(pool) overload.
5. “What silently breaks when you add .parallel() to working code?”
Testing: Three categories, no exceptions raised.
Scoring
Pass: Shared mutable accumulators become races, non-associative reductions start depending on the core count, and forEach ordering disappears. None of them throws.
Fail: Says nothing breaks because streams are functional.
6. “Does parallel lose encounter order?”
Testing: The nuance most people get wrong in both directions.
Scoring
Pass: Not for collect or toList — each worker accumulates separately and results merge in order. forEach is unordered; forEachOrdered restores it and gives up much of the benefit.
Fail: Says order is always lost, or always kept.
7. “Why must a reduce operator be associative?”
Testing: Can they give a failing example?
Scoring
Pass: The stream is split, reduced independently and combined, so a non-associative operator gives an answer that depends on the split. Subtraction or pairwise averaging is right on one machine and wrong on another.
Fail: Repeats the word associative without an example.
8. “What makes a source good or bad for parallelism?”
Testing: Splitting cost, not just size.
Scoring
Pass: Arrays and ArrayList split by index and are ideal. LinkedList has to be walked, and Stream.iterate cannot be split usefully at all — so no amount of data helps.
Fail: Thinks only the element count matters.
9. “When would you actually use one?”
Testing: Whether they will decline it.
Scoring
Pass: CPU-bound work, a large array-backed source, no IO, no shared state, an associative reduction, and spare cores — after measuring. For blocking IO on 21, virtual threads.
Fail: Reaches for it as a general speed-up.