集合中的Iterator抛出的ConcurrentModificationException源码分析

主题:ConcurrentModificationException的集合迭代器归属

1.正常抛出超出边界等异常


List<Integer> list;  
//添加元素等  
int i = list.size();  
for (int n = 0; n < i; n++) {  
    if (list.get(n).equals(1)) {  
        list.remove(n);  
    }  
}  
//如果list.get(n)的n超出边界,抛出异常  


2.认识fail-fast的集合检测机制

“快速失败”也就是fail-fast,它是 Java 集合的一种错误检测机制。当多个线程对集合进行结构上的改变的操作时,有可能会产生fail-fast机制。记住是有可能,而不是一定。例如:假设存在两个线程(线程1、线程2),线程1通过Iterator在遍历集合A中的元素,在某个时候线程2修改了集合A的结构(是结构上面的修改,而不是简单的修改集合元素的内容),那么这个时候程序就会抛出 ConcurrentModificationException 异常,从而产生fail-fast机制。

一.ArrayList分析

里面的Itr迭代类检测是否在原来的list进行修改方法

Itr的成员变量
        int cursor;       // index of next element to return
        int lastRet = -1; // index of last element returned; -1 if no such
        int expectedModCount = modCount;//跟随迭代器


List的成员变量
       protected transient int modCount = 0;//remove等元素操作加1


//下面就是迭代器的快速失败的原理
final void checkForComodification() {
            if (modCount != expectedModCount)
                throw new ConcurrentModificationException();
        }

所以要进行remove等操作,请使用迭代器的remove,请看Itr的remove源码

此时 Itr的expectedModCount改变,所以checkForComodification()不会抛出该异常,而且同步更新Itr和当前list的元素

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();
            }
        }

二.HashMap的Map集合

原理也是有这样的一个检测方法,是集合修改等操作,请到set集合中修改,比如:
        Iterator it = hs.keySet().iterator();
        while (it.hasNext()) {
            String str = (String) it.next();
            System.out.println(hs);
            it.remove();//修改的是set,同步更新到map集合
        }




  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值