ArrayList не синхронизируется из коробки.
Реализация массива изменяемого размера
Список интерфейса. Реализует все
необязательные операции со списком и разрешения
все элементы, включая ноль. В
дополнение к реализации списка
интерфейс, этот класс предоставляет методы
манипулировать размером массива
который используется внутри для хранения
список. (Этот класс примерно
эквивалентно Vector, за исключением того, что оно
не синхронизирован.)
Это позволяет избежать некоторых проблем с производительностью в ситуациях, когда вы знаете, что вам не понадобится безопасность потоков (например, полностью инкапсулированные личные данные). Однако и у ArrayList, и у Vector есть проблемы при использовании итераторов над ними: при итерации по любому типу коллекции, если данные добавляются или удаляются, вы выбросите исключение ConcurrentModificationException :
Обратите внимание, что эта реализация не
синхронизированы. Если несколько потоков
получить доступ к экземпляру ArrayList
одновременно, и по крайней мере один из
темы изменяет список
структурно он должен быть синхронизирован
внешне. (Структурная модификация
любая операция, которая добавляет или удаляет
один или несколько элементов, или явно
изменяет размер резервного массива; просто
установка значения элемента не
структурная модификация.) Это
обычно достигается
синхронизация на некотором объекте, который
естественно инкапсулирует список. Если нет
такой объект существует, список должен быть
"завернутый" с помощью
Метод Collections.synchronizedList.
Это лучше всего сделать во время создания, чтобы
предотвратить случайные несинхронизированные
доступ к списку:
Список списка =
Collections.synchronizedList (новый
ArrayList (...));
Итераторы, возвращаемые этим классом
методы итератора и listIterator
безотказный: если список структурно
изменено в любое время после
итератор создается, кроме как
через собственное удаление итератора или
добавить методы, итератор бросит
ConcurrentModificationException. Таким образом,
перед лицом одновременного
модификация, итератор не работает
быстро и чисто, а не
риск произвольный, недетерминированный
поведение в неопределенное время в
будущее.
Обратите внимание, что отказоустойчивое поведение
итератор не может быть гарантирован
вообще говоря, невозможно
сделать какие-либо жесткие гарантии в
наличие несинхронизированного одновременного
модификация. Отказоустойчивые итераторы
бросить ConcurrentModificationException
на основе максимальных усилий. Следовательно, это
было бы неправильно написать программу, которая
зависело от этого исключения для его
правильность: безотказное поведение
итераторы должны использоваться только для
обнаруживать ошибки.
ArrayList имеет множество полезных ароматов, а Vector - нет. Мой личный фаворит - CopyOnWriteArrayList :
Потокобезопасный вариант ArrayList, в котором все мутационные операции (добавление, установка и т. Д.) Реализованы путем создания новой копии базового массива.
Обычно это слишком дорого, но может быть более эффективным, чем альтернативы, когда операции обхода значительно превосходят число мутаций, и полезно, когда вы не можете или не хотите синхронизировать обходы, но при этом необходимо исключить помехи между параллельными потоками. Метод итератора в стиле «снимок» использует ссылку на состояние массива в момент создания итератора. Этот массив никогда не изменяется в течение времени жизни итератора, поэтому вмешательство невозможно, и итератор гарантированно не генерирует исключение ConcurrentModificationException. Итератор не будет отражать добавления, удаления или изменения в списке с момента его создания. Операции изменения элементов на самих итераторах (удаление, установка и добавление) не поддерживаются. Эти методы генерируют исключение UnsupportedOperationException.
CopyOnWriteArrayLists чрезвычайно полезны в работе с графическим интерфейсом, особенно в ситуациях, когда вы отображаете обновленный набор данных (например, перемещаете значки на экране). Если вы можете допустить, чтобы отображаемый список данных был на один кадр устаревшим (поскольку ваш поток производителя немного отстает от вашего потока графического обновления), CopyOnWriteArrayLists являются идеальной структурой данных.