Обзор ArrayList:
ArrayList реализован на основе массивов и является динамическим массивом, чья емкость может автоматически расти, аналогично динамической памяти применения на языке C, что динамически увеличивает память.
ArrayList не является потоком и может использоваться только в однопользованной среде. В многопоточной среде вы можете рассмотреть возможность использования функции Collections.synchronizedList (List L) для возврата класса ArrayList, защищенного потоком, или вы можете использовать класс CopyOnWritearRayList в одновременном параллельном пакете.
ArrayList реализует сериализуемый интерфейс, поэтому он поддерживает сериализацию, может быть передана посредством сериализации, реализует интерфейс случайного акцента и поддерживает быстрый случайный доступ. На самом деле, это быстрый доступ через серийный номер индекса, реализует клонируемый интерфейс и может быть клонирован.
Каждый экземпляр ArrayList имеет емкость, которая относится к размеру массива, используемого для хранения списков. Это всегда, по крайней мере, равно размеру списка. Поскольку элементы постоянно добавляются в ArrayList, их емкость также увеличивается автоматически. Автоматический рост приведет к привлечению данных в новый массив, поэтому, если вы можете предсказать объем данных, вы можете указать его емкость при построении массива. Перед добавлением большого количества элементов приложение также может использовать операцию EncureCapacity для увеличения емкости экземпляра ArrayList, что может уменьшить количество дополнительных перераспределений.
Обратите внимание, что эта реализация не является синхронной. Если несколько потоков получают доступ к экземпляру ArrayList одновременно, и, по крайней мере, один из потоков структурно изменяет список, он должен оставаться внешне синхронизированным.
Давайте сделаем запись и резюме Java Arraylist
открытый класс ArrayList <e> { / *** Элементы, которые хранят коллекцию** / private Transient объект [] elementData; / ** Размер элемента*/ private int size;Определите общий класс, массив объекта и личную переменную, чтобы записать количество элементов в коллекции. В исходном тексте есть дополнительная частная переменная, и я не знаю, что ее использовать, и у автора нет объяснения или упоминания. Это нормально, если я не использовал его.
/ ** * Инициализировать в соответствии с указанным размером * @param initialcapacity */ public arraylist (int initialCapacity) {super (); if (initialCapacity <= 0) {// Исключение бросает new allogalargumentException («Параметр инициализации не может быть меньше 0»); } else {// инициализируйте массив this.elementData = new Object [initialCapacity]; }} / *** Инициализация по умолчанию* / public arraylist () {this (10); } /*** Инициализировать в соответствии с классом коллекции* @param c класс, который должен унаследовать интерфейс коллекции* /public arraylist (collection <? Extends e> c) {// инициализировать elementdata = c.toarray (); size = elementData.length; // конвертировать тип объекта if (elementData.getClass ()! = Object []. Class) {elementData = arrays.copyof (elementdata, size, object []. Class); }} 3 Методы инициализации, инициализируйте массив в соответствии с размером по умолчанию, инициализируйте заданный размер и пропустите класс, который наследует интерфейс коллекции коллекции для инициализации назначения конверсии
/ *** Коллекция расширения* @param mincapacity*/ public void evidecapacity (int mincapacity) {/ ** Текущий размер массива*/ int oldCapacity = elementData.length; if (minCapacity > oldCapacity) { /** * Although oldData is not used, this is about memory management and the Arrays.copyOf() method is not thread-safe* oldData refers to the elementData variable during the life cycle of if, so it will not be recycled by GC* When the Arrays.copyOf() method copies elementData to newCapacity, it can prevent new memory or other threads from выделение памяти памяти ElementData от вторжения. * Когда конец уходит, если, цикл OldData заканчивается и переработан*/ Object OldData [] = elementData; int newcapacity = (OldCapacity * 3)/2 + 1; // увеличить 50%+1 if (newcapacity <mincapacity) newcapacity = mincapacity; // Использовать Arrays.copyof для копирования элементов коллекции и генерирования нового массива elementdata = arrays.copyof, newcapacity); }}Это основной метод. Расширение набора фактически состоит в том, чтобы сравнить расширение массива и размер коллекции Mincapacity, чтобы определить, следует ли его расширить. Метод Arrays.copyof () используется для расширения.
Оригинальный текст имеет подробное объяснение. Этот метод копирует содержание первого параметра в новый массив. Размер массива является вторым параметром и возвращает новый массив. Есть подробные комментарии о переменных OldData.
/ *** Проверьте, выходит ли индекс из границ* @param index*/ private void rangecheck (int index) {if (index> size || index <0) {бросить новый индекстуфундсексапс («Индикатор превышает, index:« + index + », size:« + size); }}Является ли поиск подписания 1 /**
* Добавить элемент* Добавить указанный элемент в конце коллекции* @param e Добавлен элемент* @return*/ public boolean add (e e) {eveRecapacity (size+1); elementData [size] = e; размер ++; вернуть истину; }Добавьте элемент, сначала разверните емкость, назначьте значение, а затем добавьте элемент один. Обратите внимание, что размер+1 размер поля не добавлен один. Вот арифметическая операция, поэтому необходимо увеличить ее позже.
/ *** Добавить элемент* добавить элемент в указанную позицию* @param Индекс указанный индекс индекс индекс Индекс Элемент элемент* @param* @return*/ public boolean add (int index, e element) {rangecheck (index); EncureCapacity (размер+1); // Элемент elementData, начиная с положения индекса и длины размера-индекса, // копирование в новую массив ElementData, начиная с позиции индекса как индекс+1. // это означает, что элемент в настоящее время находится в этой позиции и все последующие элементы перемещаются прямо на одну позицию. System.ArrayCopy (ElementData, Index, ElementData, Index+1, Size-Index); elementData [index] = element; size ++; // добавить элемент one return true; }Разница здесь-System.ArrayCopy (ElementData, Index, ElementData, Index+1, Size-Index);
Это внутренний метод c. У подробного оригинального текста есть объяснение, поэтому я не буду говорить об этом здесь. Это также является ядром всего ArrayList, а также принципа внутренней реализации Arrays.copyof ()
/*** Добавьте все элементы* Добавьте все элементы в коллекцию в конец этого списка в порядке элементов, возвращаемых итератором указанной коллекции. * @param c * @return */ public boolean addall (collection <? Extends e> c) {Object [] newElement = c.toarray (); int elementLength = newElement.length; EncureCapacity (размер+elementLength); // Из индекса NewElement 0, ElementLength Elements, ElementData Size System.ArrayCopy (NewElement, 0, ElementData, Size, ElementLength); размер+= elementLength; возврат ElementLength! = 0; }По сути, другие методы выполняют различную обработку только в соответствии с различными ситуациями, такими как передача объектов данных через интерфейс и получение длины для расширения, а также копирование данных в новый массив с использованием системы и Arraycopy.
/ *** Укажите позицию, добавьте все элементы* @param Index Index Index Position* @param c вставленные элементы коллекция* @return*/ public boolean addall (int index, collection <? Extends e> c) {if (index> size || index <0) {throw New Indexoutofboundsexception ("index:" + index + ", size); } Object [] newElement = c.toarray (); int elementLength = newElement.length; EncureCapacity (размер+elementLength); int nummoved = size-index; // Судите, находится ли позиция вставки в середине массива if (nummoved> 0) {// Перемещать все элементы за позицией вставки индекса назад // Вставить элементы Nummoed, начиная с индекса индекса индекса индекса в индекс+elementLength Degin Data System. Arraycopy (elementData, index, elementData, indextemy letlement); } // Добавить длину elementLement в NewElement от 0 до позиции, где elementData Index запускает System.ArrayCopy (NewElement, 0, ElementData, Index, ElementLength); размер += elementLength; возврат ElementLength! = 0; } / ** * Укажите значение индекса * @param index * @param element * @return * / public e set (int index, e element) {rangecheck (index); E OldElement = (e) elementData [index]; elementData [index] = element; вернуть OldElement; } / ** * Получить значение на основе индекса * @param index * @return * / public e get (int index) {rangecheck (index); return (e) elementdata [index]; } / *** Удалить элемент в соответствии с SPUPCREPT* @param Index* / public E Remove (int index) {rangeCheck (index); E OldElement = (e) elementData [index]; / ** Количество элементов после удаленного индекса*/ int nummoved = size-index-1; // Если он перемещается в диапазоне массива, если (Nummoved> 0) System.ArrayCopy (elementData, Index+1, ElementData, Index, Nummoved); // Удалить elementData [-size] = null; вернуть OldElement; } /** * Удалить в соответствии с элементом * @param obj * @return * /public boolean remove (Object obj) {// ArrayList допускает NULL, поэтому обработка суждения также должна быть выполнена, если (obj == null) {for (int index = 0; index <size; index ++) {if (elementData [index] == null); вернуть истину; }}} else {for (int index = 0; index <size; index ++) {if (obj.equals (elementData [index])) {remove (index); вернуть истину; }}} вернуть false; } / *** Удалить элементы в указанном диапазоне в соответствии с инспектом* @param fromindex start* @param toindex end* / protected void remormentange (int fromindex, int toindex) {rangecheck (fromindex); Rangecheck (toindex); // количество элементов, которые должны быть перемещены int nummoved = size - toindex; // переместить элемент позади toIndex в system от fromindex.arraycopy (elementdata, toindex, elementdata, fromindex, Nummoved); // количество элементов, которые должны быть удалены int newsize = size- (toindex-fromindex); while (size! = newsize) {elementData [-Size] = null; }} / *** Регулируйте емкость массива на фактическую емкость* / public void trimtosize () {int length = elementData.length; if (size <leng) {Object [] old = elementData; elementData = arrays.copyof (elementdata, size); }} / *** Преобразовать элементы сбора в массив* @return* / public object [] toarray () {return arrays.copyof (elementdata, size); } public <t> t [] toarray (t [] a) {if (a.length <size) {return (t []) arrays.copyof (elementdata, size, a.getclass ()); } // Скопировать элемент сбора в массив asystem.arraycopy (elementData, 0, a, 0, size); if (a.length> size) {for (int index = size; index <a.length; index ++) {a [index] = null; }} вернуть a; } По сути, речь идет о эксплуатации массива и использовании методов C для назначения значений и их перемещения. Вы можете просмотреть исходный текст подробно. В исходном тексте не так много проблем, за исключением частной переменной, и код может работать идеально. Трудностью этого и использование переменной OldData в методе расширения будет два метода системы, Arraycopy и Arryast.copy () и использование переменной OldData в методе расширения. Эта переменная действительно хороша. Вначале я не знал, почему я использовал это так, и я объясню это в конце исходного текста.
Выше приведено примером объяснения реализации Java Arraylist, введенного вам редактором. Я надеюсь, что это будет полезно для вас. Если у вас есть какие -либо вопросы, пожалуйста, оставьте мне сообщение. Редактор ответит вам вовремя. Большое спасибо за вашу поддержку на веб -сайте Wulin Network!