13)从头开始遍历元素,返回第一个和目标元素相等的元素索引,如果不存在,则返回 -1。
/** * 从头开始遍历元素,返回第一个和目标元素相等的元素索引,如果不存在,则返回 -1 */ @Override public int indexOf(Object o) { /** * 返回第一个匹配元素的索引 */ if (o == null) { for (int i = 0; i < this.size; i++) { if (this.elementData[i]==null) { return i; } } } else { for (int i = 0; i < this.size; i++) { if (o.equals(this.elementData[i])) { return i; } } } return -1; }
14)从尾部开始遍历元素,返回第一个和目标元素相等的元素索引,如果不存在,则返回 -1。
/** * 从尾部开始遍历元素,返回第一个和目标元素相等的元素索引,如果不存在,则返回 -1 */ @Override public int lastIndexOf(Object o) { /** * 返回第一个匹配元素的索引 */ if (o == null) { for (int i = this.size-1; i >= 0; i--) { if (this.elementData[i]==null) { return i; } } } else { for (int i = this.size-1; i >= 0; i--) { if (o.equals(this.elementData[i])) { return i; } } } return -1; }
15)ArrayList 中是否包含和目标元素相等的元素,如果包含,则返回 true;否则返回 false。
/** * 从头开始遍历,并通过 {@link Object#equals(Object)} 方法获取相等元素的索引 */ @Override public boolean contains(Object o) { return this.indexOf(o) >= 0; }
16)ArrayList 中当前元素的个数
/** * 当前元素个数 * created by ZXD at 15 Jul 2018 T 11:25:21 * @return */ @Override public int size() { return this.size; }
17)ArrayList 是否为空
/** * 是否为空 * created by ZXD at 15 Jul 2018 T 11:25:48 * @return */ @Override public boolean isEmpty() { return this.size == 0; }
18)将 ArrayList 的容量缩小为当前元素的个数,以减少 ArrayList 的内存占用,适合于静态 ArrayList 实例。
/** * 将 ArrayList 的容量缩小为当前元素的个数,以减少 ArrayList 的内存占用。 */ public void trimToSize() { // 结构修改计数器 modCount++; /** * 当元素个数小于对象数组长度时,缩小其容量为元素个数,降低 ArrayList 的内存占用。 */ if (this.size < this.elementData.length) { this.elementData = this.size == 0 ? ArrayList.EMPTY_ELEMENTDATA : Arrays.copyOf(this.elementData, this.size); } }
19)如果需要,则增加 ArrayList 的容量以满足最少能容纳 minCapacity 个元素。
/** * 增加 ArrayList 的容量以满足最少能容纳 minCapacity 个元素 */ public void ensureCapacity(int minCapacity) { /** * 预期容量大于可用容量时执行扩容操作 */ if (minCapacity > this.elementData.length && !(this.elementData == ArrayList.DEFAULTCAPACITY_EMPTY_ELEMENTDATA && minCapacity <= ArrayList.DEFAULT_CAPACITY)) { modCount++; this.grow(minCapacity); } }
20)将 ArrayList 转换为指定类型的对象数组,包含所有元素。
@Override @SuppressWarnings("unchecked") public <T> T[] toArray(T[] a) { /** * 形参数组的长度小于 ArrayList 的 size,则默认复制 ArrayList 的所有元素, * 长度为 ArrayList 的 size。 */ if (a.length < this.size) { return (T[]) Arrays.copyOf(this.elementData, this.size, a.getClass()); } System.arraycopy(this.elementData, 0, a, 0, this.size); /** * 复制 ArrayList 的所有元素,并将索引为 size 的元素设置为 null,返回新数组 */ if (a.length > this.size) { a[this.size] = null; } return a; }
21)将 ArrayList 实例转换为 Object 对象数组
/** * 返回包含 ArrayList 所有元素的对象数组 */ @Override public Object[] toArray() { // 拷贝出 ArrayList 中存储在底层对象数组中的所有元素 return Arrays.copyOf(this.elementData, this.size); }
22)使用函数式接口顺序消费 ArrayList 中的每个元素,出现并发修改时,之前消费的元素不能回滚
/** * 顺序消费 ArrayList 中的每个元素 */ @Override public void forEach(Consumer<? super E> action) { Objects.requireNonNull(action); // 缓存并发修改计数值 final int expectedModCount = modCount; // 读取底层对象数组 final Object[] es = this.elementData; // 读取元素个数 final int size = this.size; // 遍历每个元素并调用函数式接口进行消费 for (int i = 0; modCount == expectedModCount && i < size; i++) { action.accept(ArrayList.elementAt(es, i)); } if (modCount != expectedModCount) { throw new ConcurrentModificationException(); } }
23)移除 ArrayList 中满足指定函数式断言的所有元素
/** * 移除 ArrayList 中满足指定函数式断言的所有元素 */ @Override public boolean removeIf(Predicate<? super E> filter) { return this.removeIf(filter, 0, this.size); } /** * Removes all elements satisfying the given predicate, from index * i (inclusive) to index end (exclusive). * 【移除所有满足指定断言的元素,包括起始索引,不包括结束索引】 */ boolean removeIf(Predicate<? super E> filter, int i, final int end) { Objects.requireNonNull(filter); int expectedModCount = modCount; final Object[] es = this.elementData; /** * 从头开始略过不满足断言的元素,找到第一个需要移除的元素索引 */ for (; i < end && !filter.test(ArrayList.elementAt(es, i)); i++) { ; } // Tolerate predicates that reentrantly access the collection for // read (but writers still get CME), so traverse once to find // elements to delete, a second pass to physically expunge. if (i < end) { final int beg = i; final long[] deathRow = ArrayList.nBits(end - beg); deathRow[0] = 1L; // set bit 0 for (i = beg + 1; i < end; i++) { if (filter.test(ArrayList.elementAt(es, i))) { ArrayList.setBit(deathRow, i - beg); } } if (modCount != expectedModCount) { throw new ConcurrentModificationException(); } expectedModCount++; modCount++; int w = beg; for (i = beg; i < end; i++) { if (ArrayList.isClear(deathRow, i - beg)) { es[w++] = es[i]; } } this.shiftTailOverGap(es, w, end); return true; } else { if (modCount != expectedModCount) { throw new ConcurrentModificationException(); } return false; } }
24)将 ArrayList 中的所有元素替换为通过二元函数式接口变换后的值,元素类型保持不变。
/** * UnaryOperator 接受类型为 E 的参数并返回类型为 E 的对象 */ @Override public void replaceAll(UnaryOperator<E> operator) { Objects.requireNonNull(operator); final int expectedModCount = modCount; final Object[] es = this.elementData; final int size = this.size; for (int i = 0; modCount == expectedModCount && i < size; i++) { // 遍历并替换 ArrayList 中的每个元素 es[i] = operator.apply(ArrayList.elementAt(es, i)); } if (modCount != expectedModCount) { throw new ConcurrentModificationException(); } modCount++; }
25)通过指定的比较器对 ArrayList 中的元素执行排序
/** * 对 ArrayList 进行排序 */ @Override @SuppressWarnings("unchecked") public void sort(Comparator<? super E> c) { final int expectedModCount = modCount; // 对对象数组内指定范围的元素执行排序 Arrays.sort((E[]) this.elementData, 0, this.size, c); if (modCount != expectedModCount) { throw new ConcurrentModificationException(); } modCount++; }
26)返回 ArrayList 的顺序迭代器
/** * 返回 ArrayList 的顺序迭代器 */ @Override public Iterator<E> iterator() { return new Itr(); } /** * An optimized version of AbstractList.Itr * 只能往后遍历,支持移除元素 */ private class Itr implements Iterator<E> { int cursor; // 下一个返回元素的索引,从 0 开始 int lastRet = -1; // 最近一个返回元素的索引 int expectedModCount = ArrayList.this.modCount; // fast-fail 机制的计数器 Itr() {} /** * 是否还有下一个元素 * created by ZXD at 15 Jul 2018 T 11:39:55 * @return */ @Override public boolean hasNext() { return this.cursor != ArrayList.this.size; } /** * 获取下一个元素 * created by ZXD at 15 Jul 2018 T 11:40:12 * @return */ @Override @SuppressWarnings("unchecked") public E next() { /** * 并发修改校验,创建迭代器时会获取外部修改计数器值并将其缓存, * 通过比较缓存值和外部计数器值来判断是否发生并发结构修改。 */ this.checkForComodification(); // 获取下一个元素的索引 final int i = this.cursor; // 元素已经全部遍历完成,并发遍历时其中有线程删除了元素时可能出现 if (i >= ArrayList.this.size) { throw new NoSuchElementException(); } final Object[] elementData = ArrayList.this.elementData; if (i >= elementData.length) { throw new ConcurrentModificationException(); } // 递增游标值 this.cursor = i + 1; // 返回目标值 return (E) elementData[this.lastRet = i]; } @Override public void remove() { if (this.lastRet < 0) { throw new IllegalStateException(); } this.checkForComodification(); try { // 移除 ArrayList 中的元素 ArrayList.this.remove(this.lastRet); // 更新游标值 this.cursor = this.lastRet; // 移除元素时,lastRet 置为 -1 this.lastRet = -1; // 更新内部的并发修改计数值 this.expectedModCount = ArrayList.this.modCount; } catch (final IndexOutOfBoundsException ex) { throw new ConcurrentModificationException(); } } /** * 顺序消费未迭代的所有元素 * created by ZXD at 15 Jul 2018 T 11:44:41 * @param action */ @Override public void forEachRemaining(Consumer<? super E> action) { Objects.requireNonNull(action); final int size = ArrayList.this.size; int i = this.cursor; if (i < size) { final Object[] es = ArrayList.this.elementData; if (i >= es.length) { throw new ConcurrentModificationException(); } // 游标值小于 size 并且未发生并发结构修改 for (; i < size && ArrayList.this.modCount == this.expectedModCount; i++) { // 使用函数式接口消费目标元素 action.accept(ArrayList.elementAt(es, i)); } // update once at end to reduce heap write traffic // 更新游标值 this.cursor = i; this.lastRet = i - 1; this.checkForComodification(); } } final void checkForComodification() { /** * 判断是否存在多线程并发修改 ArrayList 实例 */ if (ArrayList.this.modCount != this.expectedModCount) { throw new ConcurrentModificationException(); } } }
27)返回 ArrayList 的列表迭代器
/** * 返回 ArrayList 的列表迭代器 */ @Override public ListIterator<E> listIterator() { return new ListItr(0); } /** * An optimized version of AbstractList.ListItr * 支持向前或向后遍历,支持在迭代过程中增加、移除、修改元素 */ private class ListItr extends Itr implements ListIterator<E> { ListItr(int index) { super(); cursor = index; } /** * 是否存在可迭代的前一个元素 * created by ZXD at 15 Jul 2018 T 11:47:17 * @return */ @Override public boolean hasPrevious() { return cursor != 0; } /** * 获取下一个迭代元素的索引 * created by ZXD at 15 Jul 2018 T 11:47:45 * @return */ @Override public int nextIndex() { return cursor; } /** * 获取前一个迭代元素的索引 * created by ZXD at 15 Jul 2018 T 11:48:02 * @return */ @Override public int previousIndex() { return cursor - 1; } /** * 获取前一个迭代元素 * created by ZXD at 15 Jul 2018 T 11:48:20 * @return */ @Override @SuppressWarnings("unchecked") public E previous() { checkForComodification(); final int i = cursor - 1; if (i < 0) { throw new NoSuchElementException(); } final Object[] elementData = ArrayList.this.elementData; if (i >= elementData.length) { throw new ConcurrentModificationException(); } // 更新游标并返回目标元素 cursor = i; return (E) elementData[lastRet = i]; } /** * 更新最后一次返回的元素 * created by ZXD at 15 Jul 2018 T 11:49:59 * @param e */ @Override public void set(E e) { if (lastRet < 0) { throw new IllegalStateException(); } checkForComodification(); try { ArrayList.this.set(lastRet, e); } catch (final IndexOutOfBoundsException ex) { throw new ConcurrentModificationException(); } } /** * 迭代过程中动态将元素插入到下一次迭代的索引处 * created by ZXD at 15 Jul 2018 T 11:50:25 * @param e */ @Override public void add(E e) { checkForComodification(); try { final int i = cursor; ArrayList.this.add(i, e); // 更新游标、最后一次返回的元素下标、结构修改计数值 cursor = i + 1; lastRet = -1; expectedModCount = ArrayList.this.modCount; } catch (final IndexOutOfBoundsException ex) { throw new ConcurrentModificationException(); } } }
28)清空 ArrayList
/** * 清空数组元素和 size */ @Override public void clear() { modCount++; final Object[] es = this.elementData; // 将对象数组前 size 个元素置为 null for (int to = this.size, i = this.size = 0; i < to; i++) { es[i] = null; } }
原文出处:https://www.cnblogs.com/zhuxudong/p/9581072.html
点击查看更多内容
为 TA 点赞
评论
共同学习,写下你的评论
评论加载中...
作者其他优质文章
正在加载中
感谢您的支持,我会继续努力的~
扫码打赏,你说多少就多少
赞赏金额会直接到老师账户
支付方式
打开微信扫一扫,即可进行扫码打赏哦