平时在遍历的时候,其实我都是用for循环遍历ArrayList的,所以没出现过什么问题,只要注意在曾删的时候,注意那些索引的变化就行了,然后就是有一次在用迭代器iterator() 进行遍历的时候,其实遍历过程中你是不能改变数值的,确切的来说是不能改变遍历的那个数组的数值(这里我就突然想到有一次在用迭代器遍历HashMap的时候,HashMap发生了改变,那个时候我就很懵,后来才发现是因为put操作是会覆盖原来的那个值的,因此可以进行改变)。。。
对于iterator() 这个方法,其实是返回ArrayList里面的内部类
public Iterator<E> iterator() {
return new Itr();
}
/**
* An optimized version of AbstractList.Itr
*/
private class Itr implements Iterator<E> {
在迭代的时候是不能进行删除的,会出异常
public E next() {
checkForComodification();
int i = cursor;
if (i >= size)
throw new NoSuchElementException();
}
但是其实迭代器里面也有个remove方法
public void remove() {
if (lastRet < 0)
throw new IllegalStateException();
checkForComodification();
try {
ArrayList.this.remove(lastRet);
cursor = lastRet;
lastRet = -1;
expectedModCount = modCount;
} catch (IndexOutOfBoundsException ex) {
throw new ConcurrentModificationException();
}
}
他就是通过expectedModCount = modCount;这个来改变值,这样就防止了出异常
所以说可以通过迭代器的remove方法进行操作,但是这个是线程不安全的,!!!
//因为他的ArrayList.this.remove其实本质上还是调用了ArrayList的remove方法
public E remove(int index) {
rangeCheck(index);
modCount++;
E oldValue = elementData(index);
int numMoved = size - index - 1;
if (numMoved > 0)
System.arraycopy(elementData, index+1, elementData, index,
numMoved);
elementData[--size] = null; // clear to let GC do its work
return oldValue;
}
//其实这个验证很简单,只要点击原本的arraylist的remove方法你就会发现其实就是在同一行
虽然说vector是保证线程安全的类,但是!!!我在另外一篇文章里面看到,其实本质还是线程不安全
!!!!!
https://www.cnblogs.com/bsjl/p/7676209.html
基于此,就是推荐使用CopyOnWriteArrayList!!!!!!!!!等我以后了解过源码后再来更新