Слайд 16
Интерфейс List, реализация ArrayList
При добавлении 11-го элемента, проверка показывает
что места в массиве нет. Соответственно создается новый массив и вызывается System.arraycopy(). После этого добавление элементов продолжается.
Добавление элемента на позицию с определенным индексом происходит в три этапа:
1) проверяется, достаточно ли места в массиве для вставки нового элемента;
2) подготавливается место для нового элемента с помощью System.arraycopy();
3) перезаписывается значение у элемента с указанным индексом.
Как можно догадаться, в случаях, когда происходит вставка элемента по индексу и при этом в вашем массиве нет свободных мест, то вызов System.arraycopy() случится дважды: первый в ensureCapacity(), второй в самом методе add(index, value), что явно скажется на скорости всей операции добавления.
В случаях, когда в исходный список необходимо добавить другую коллекцию, да еще и в «середину», стоит использовать метод addAll(index, Collection). И хотя, данный метод скорее всего вызовет System.arraycopy() три раза, в итоге это будет гораздо быстрее поэлементного добавления.
С удалением элемента по индексу всё достаточно просто. Сначала определяется какое количество элементов надо скопировать. Затем копируем элементы используя System.arraycopy(). Уменьшаем размер массива и забываем про последний элемент.
При удалении по значению, в цикле просматриваются все элементы списка, до тех пор пока не будет найдено соответствие. Удален будет лишь первый найденный элемент.
При удалении элементов текущая величина capacity не уменьшается, что может привести к своеобразным утечкам памяти. Поэтому не стоит пренебрегать методом trimToSize().
Итоги. - Быстрый доступ к элементам по индексу за время O(1);
- Доступ к элементам по значению за линейное время O(n);
- Медленный, когда вставляются и удаляются элементы из «середины» списка;
Если вам необходимо часто добавлять или удалять элементы коллекции, то предпочтительней использовать LinkedList.