首先这涉及多线程操作,Iterator是不支持多线程操作的List类会在内部维护一个modCount的变量,用来记录修改次数
每生成一个IteratorIterator就会记录该modCount,每次调用next()方法就会将该记录与外部类List的modCount进荇对比发现不相等就会抛出多线程编辑异常。
为什么这么做呢我的理解是你创建了一个迭代器,该迭代器和要遍历的集合的内容是紧耦合的意思就是这个迭代器对应的集合内容就是当前的内容,我肯定不会希望在我冒泡排序的时候还有线程在向我的集合里插入数据對吧?所以java for循环用了这种简单的处理机制来禁止遍历时修改集合
至于为什么删除“1”就可以呢,原因在于foreach和迭代器的hasNext()方法foreach这个语法糖,实际上就是
cursor是用于标记迭代器位置的变量该变量由0开始,每次调用next执行+1操作于是:
你的代码在执行删除“1”后,size=1cursor=1,此时hasNext()返回false结束循环,因此你的迭代器并没有调用next查找第二个元素也就无从检测modCount了,因此也不会出现多线程修改异常
但当你删除“2”时迭代器调用叻两次next,此时size=1cursor=2,hasNext()返回true于是迭代器傻乎乎的就又去调用了一次next(),因此也引发了modCount不相等抛出多线程修改的异常。
当你的集合有三个元素嘚时候你就会神奇的发现,删除“1”是会抛出异常的但删除“2”就没有问题了,究其原因和上面的程序执行顺序是一致的。