Чем fail-fast итератор отличается от weakly consistent?
- Почему итератор ConcurrentHashMap не бросает ConcurrentModificationException?
Fail-fast итератор (ArrayList, HashMap) замечает структурное изменение коллекции не через него и бросает ConcurrentModificationException — по возможности, без гарантии. Weakly consistent (ConcurrentHashMap, ConcurrentLinkedQueue) не падает, обходит каждый элемент не больше раза и может увидеть часть параллельных изменений.
- Fail-fast основан на счётчике modCount — это отладочный механизм, не синхронизация
- CopyOnWriteArrayList — snapshot-итератор: видит копию на момент создания
- CME возникает и в одном потоке — удаление в for-each
А ещё Полагаться на CME для логики программы нельзя
Подробно
Fail-fast. Коллекция ведёт счётчик структурных изменений modCount (добавление, удаление; замена значения — нет). Итератор при создании запоминает его и сверяет в каждом next(). Не совпало — CME. Цель — быстро сообщить об ошибке вместо странного поведения. Гарантии нет: в многопоточном коде без синхронизации изменение может быть не замечено.
Weakly consistent — итераторы коллекций java.util.concurrent:
- не бросают CME;
- каждый элемент, присутствовавший при создании итератора и не удалённый, будет возвращён ровно один раз;
- изменения после создания итератора могут быть видны или нет.
Подходят для обхода разделяемых структур под нагрузкой (мониторинг, сбор статистики), но не дают консистентного снимка.
Snapshot — CopyOnWriteArrayList: итератор работает с копией массива на момент создания, изменения не видны, remove через итератор не поддерживается.
Что хотят услышать
- Механика fail-fast и modCount.
- Гарантии weakly consistent.
- Snapshot-итераторы.
Частые ошибки
- Считать fail-fast механизмом потокобезопасности.
Проверьте себя
Один верный вариант. Подумайте, потом откройте ответ.
Показать варианты и ответ
- ✗fail-fast потокобезопасен
- ✓fail-fast бросает CME при изменении во время обхода; weakly consistent — не бросает
- ✗weakly consistent бросает ConcurrentModificationException, а fail-fast молча пропускает изменения
- ✗Они идентичны
Что спросят дальше
- Как безопасно удалить элемент при обходе?
- Что делает CopyOnWriteArrayList?
Разбор темы
- Конкурентные коллекции
ConcurrentHashMap без сегментов (CAS + блокировка бакета), запрет null, CopyOnWriteArrayList и BlockingQueue.
- Итераторы: fail-fast и ConcurrentModificationException
Iterator и ListIterator, механизм modCount, причины CME даже в одном потоке и безопасное удаление.
Связанные вопросы
Разбор собеседования с sotto
После собеседования sotto разбирает разговор: оценка, каждый вопрос — хорошо, частично или слабо, чего не хватило в ответе и над чем поработать к следующему разу. Первые 30 минут бесплатно.