Collectors.toMap() без merge-функции — рабочий код до первого дубликата ключа

stream.collect(Collectors.toMap(keyFn, valueFn)) компилируется, проходит код-ревью и работает на тестовых данных, где ключи уникальны. Проблема появляется в проде, когда среди элементов встречаются два с одинаковым ключом.

В этот момент toMap бросает IllegalStateException: Duplicate key ... — без предупреждения, прямо в рантайме. Метод не выбирает «оставить первый» или «оставить последний» сам, потому что такого поведения по умолчанию у него нет.

Map byEmail = users.stream() .collect(Collectors.toMap( User::getEmail, u -> u, (existing, replacement) -> replacement ));

Третий аргумент — merge-функция — обязателен, если дубликаты ключей вообще возможны. Без него любой toMap на реальных данных — отложенная бомба.

Спросят, почему Collectors.groupingBy() не бросает то же исключение на дубликатах. Потому что groupingBy по умолчанию складывает значения в List через merge-логику коллекции, а не заменяет одно значение другим — конфликт ключей там ожидаемое поведение, а не ошибка.

Если ключ выведен из данных, а не из искусственного счётчика — merge-функция не опция, а часть контракта.

Тренажёр: 600 вопросов, мок с таймером, план повторов

senior·base — что спрашивают на самом деле


В этом посте были ссылки, но мы их удалили по правилам Сетки