Вопрос с собеседования · Java

В каких случаях parallel stream, скорее всего, не даст выигрыша или окажется медленнее последовательного?

MiddleМногопоточность
Коротко

Выигрыша нет, когда мало данных или дешёвая операция (N × Q мало), источник плохо делится (LinkedList, Stream.iterate, итератор), есть сохранение порядка (forEachOrdered, limit, findFirst) или дорогое слияние (collect в коллекции).

  • Хорошо делятся массивы, ArrayList, IntStream.range
  • Упаковка Integer съедает выигрыш — примитивные стримы
  • Общий пул делят с другими задачами

А ещё Решают только измерения (JMH)

Подробно

Практическое правило звучит как произведение числа элементов на стоимость обработки одного: пока оно мало, параллелизм только добавляет расходов на разбиение, передачу задач и слияние результатов. Хорошо делятся источники с произвольным доступом и известным размером — массивы, ArrayList, IntStream.range; плохо — связные списки и потоки, размер которых заранее неизвестен. Дорогое слияние тоже способно съесть выигрыш: например, сборка в неупорядоченный набор дешевле, чем в упорядоченный список. Отдельно стоит помнить про ловушки корректности: forEach в параллельном стриме не гарантирует порядок (для порядка есть forEachOrdered), а любые побочные эффекты на общем изменяемом состоянии дают гонки. Неизменяемость элементов, напротив, параллелизму только помогает.

Что хотят услышать

  • Условия, при которых параллелизм вредит.
  • Хорошие и плохие источники.

Частые ошибки

  • Ставить .parallel() без замера и без учёта размера данных.
  • Изменять общее состояние из параллельного стрима.

Проверьте себя

Несколько верных вариантов. Подумайте, потом откройте ответ.

Показать варианты и ответ
  • ✗Элементы коллекции неизменяемы, поэтому потокам приходится копировать их перед обработкой
  • ✓Коллекция мала, а операция дешёвая — разбиение и слияние дороже
  • ✓Источник плохо делится: LinkedList или поток из итератора
  • ✓Нужно сохранять порядок, или слияние результатов само дорого

Что спросят дальше

  • Почему ArrayList делится лучше, чем LinkedList?
  • Чем forEach отличается от forEachOrdered?

Разбор темы

Связанные вопросы

Партнёр платформы

Разбор собеседования с sotto

После собеседования sotto разбирает разговор: оценка, каждый вопрос — хорошо, частично или слабо, чего не хватило в ответе и над чем поработать к следующему разу. Первые 30 минут бесплатно.

Разбор собеседования