ArrayList有两种迭代器实现,都是按照索引查找,但比正常for循环多了并发操作的安全校验:
1. Itr()的实现,主要功能-后序遍历next()方法
public Iterator<E> iterator() { return new Itr();}
public E next() { checkForComodification(); int i = cursor; if (i >= size) throw new NoSuchElementException(); Object[] elementData = ArrayList.this.elementData; if (i >= elementData.length) throw new ConcurrentModificationException(); cursor = i + 1; return (E) elementData[lastRet = i];}其中i >= elementData.length的校验非常疑惑,理论上elementData的扩容的等操作size应该小于elementData.length,不知道在什么并发场景下会触发??
public void remove() { if (lastRet < 0) throw new IllegalStateException(); // 调用remove()方法前,必须调用next()方法,给lastRet赋值 checkForComodification(); try { ArrayList.this.remove(lastRet); cursor = lastRet; lastRet = -1; // 重置索引位 expectedModCount = modCount; // 重置modify次数,因此在iterator方法中,不能使用remove(object) } catch (IndexOutOfBoundsException ex) { throw new ConcurrentModificationException(); }}
2. ListIterator继承自Itr类,主要功能扩展-前序遍历previous(), set()以及add()方法
public ListIterator<E> listIterator() { return new ListItr(0);}
public ListIterator<E> listIterator(int index) { if (index < 0 || index > size) // 前序遍历第一个元素cursor - 1 throw new IndexOutOfBoundsException("Index: "+index); return new ListItr(index);}
ListItr(int index) { super(); cursor = index; // 初始值范围 [0, size]}
public E previous() { checkForComodification(); int i = cursor - 1; // 对比和Itr迭代的区别 if (i < 0) throw new NoSuchElementException(); Object[] elementData = ArrayList.this.elementData; if (i >= elementData.length) throw new ConcurrentModificationException(); cursor = i; return (E) elementData[lastRet = i];}
原文地址:https://www.cnblogs.com/septemberFrost/p/12017191.html
时间: 2024-10-14 23:40:07