迭代器使用过程中为什么抛出ConcurrentModificationException
出现的场景:在迭代器对集合进行遍历的同时,集合本身进行变更操作(add(), remove(), set())。
当正常调用时:
import java.util.ArrayList;
import java.util.Iterator; public class TestDemo {
public static void main(String[] args) {
ArrayList<Integer> a = new ArrayList<>();
a.add(1);
a.add(3);
a.add(5);
a.add(6);
Iterator<Integer> iterator = a.iterator();
while (iterator.hasNext()){
System.out.print(iterator.next()+" ");
}
}
}
结果:

当调用interator()接口里面的remove()操作时:

结果:

当调用ArrayList的对象下的remove()或者add();

或者

便会报错:

那么为何会出现这种情况呢?
首先我们应该知道,ArrayList底层的modCount这个属性,这也是个版本记录号每对ArrayList进行一次增删改操作,都会进行modCount++操作。并且在迭代器的使用中,会将当前的modCount的值赋给expectedModCount迭代器的这个属性。
我们先来看看得ArrayList内地迭代器的部分源码:

可以看到每次Iterator的对象调用next()操作时,都会调用checkForComodification()的方法,具体我们来看看这个方法。

再来看看迭代器中的remove()方法:

可以看到迭代器中的remove()方法虽然也是用的ArrayList的remove()方法,正如前面所说,那也会对modCount的值进行改变,但是关键就在于expectedModCount = modCount,它会将改变的值重新赋给expectedModCount。然后每次用完迭代器中的remove()方法后,就算再次用nex()的方法,调用checkForComodification()方法,就不会抛出异常。但是如果直接用ArrayList的对象调用增删改的方法,modCount值得改变,不会引起expectedModCount值的变化,再次调用迭代器,调用到checkForComodification()方法时,便会抛出ConcurrentModificationException的错误。
总的来说,在调用迭代器的时候,就用迭代器的remove()方法,否则就会出现错误,还有迭代器的一个对象只能进行一次迭代,要多次迭代,,便要创建多个对象。
迭代器使用过程中为什么抛出ConcurrentModificationException的更多相关文章
- lambda表达式中无法抛出受检异常!
抛出受检异常的时候,我们的接口应该带上throw关键字,但通过lambda表达式实现的Consumer的accept方法并不带有关键字,因此在lambda表达式中不能抛出受检异常必须把它吃掉
- 0xe7f001f0!?NDK调试过程,无故抛出SIGSEGV。
arm调试过程,如果抛一个SIGSEGV,地址在 0xe7f001f0 附近,原因居然是因为我在调试.当我使用n指令跳到下一行代码时,往往变成了continue指令一样地执行.还不确定地抛出SIGSE ...
- JAVA 语言如何进行异常处理,关键字: throws,throw,try,catch,finally分别代表什么意义? 在try块中可以抛 出异常吗?
Java通过面向对象的方法进行异常处理,把各种不同的异常进行分类, 并提供了良好的接口. 在 Java中,每个异常都是一个对象,它是 Throwable 类或其它子类的实例.当一个方法出 ...
- Swift 中异常抛出和四种异常处理
在Swift中你可以像其他语言一样抛出异常处理异常,今天我们就详细地说说Swift中的异常抛出和处理. 在一开始我们要定义错误或者说是异常,Swift中的一些简单异常可以使用枚举定义,注意这个枚举要继 ...
- C# 中异常抛出捕获机制--throw / try,catch,finally
try { messagebox.show("true"); } catch { messagebox.show("false"); } finally { m ...
- java异常处理 throw RuntimeException时不需要同时方法中声明抛出throws 异常等待调用者catch进行捕获 子父类异常问题
package com.swift.exception1; public class Demo_Exception { public static void main(String[] args) { ...
- ArrayList迭代修改抛出ConcurrentModificationException
extends:http://www.cnblogs.com/dolphin0520/p/3933551.html Iterator<Integer> iterator = list.it ...
- ArrayList中的modCount与ConcurrentModificationException
在看ArrayList源码时,看到了一个字段modCount.在add.remove.clear等方法中都有modCount++的操作.不明白什么意思.点进去看了看该字段的解释,总算明白了.modCo ...
- SilverLight抛出 System.InvalidOperationException: 超出了2083 的最大URI
在SilverLight中对于抛出 System.InvalidOperationException: 超出了 2083 的最大 URI 长度 的异常 处理 其实很简单 在 EntityFramewo ...
随机推荐
- RegExp类型
一.创建正则表达式的方法 1.字面量形式 var expressiion=/pattern/flags; flags:g全局模式,即将被应用于所有字符串,而非在发现第一个匹配项时立即停止: i不区分大 ...
- 关于DOM的一些基础问题
什么是 DOM? DOM 是一项 W3C (World Wide Web Consortium) 标准,全称是文档对象模型(Document Object Model). DOM 定义了访问文档的标准 ...
- HBuider快捷键
朋友推荐用Hbuilder编辑器,看了下Hbuilder官网和那视频,感觉牛逼哄哄的, 自己也就体验了一下,打开Hbuilder的快捷键列表,每个快捷键都体验了一下,以下展示出来的,每一个都是精华,每 ...
- Python--day72--Cookie和Session内容回顾
1. Cookie是什么 保存在浏览器端的键值对 为什么要有Cookie? 因为HTTP请求是无状态的 Cookie的原理? 服务端可以在返回响应的时候 做手脚 在浏览器上写入键值对(Cookie) ...
- P1041 查找元素
题目描述 现在告诉你一个长度为 \(n\) 的有序数组 \(a_1, a_2, ..., a_n\) ,以及 \(q\) 次询问,每次询问会给你一个数 \(x\) ,对于每次询问,你需要确定在数组中是 ...
- linux strace 命令
有时小问题可以通过观察用户空间的应用程序的行为来追踪. 监视程序也有助于建立对驱 动正确工作的信心. 例如, 我们能够对 scull 感到有信心, 在看了它的读实现如何响应 不同数量数据的读请求之后. ...
- H3C配置Hybrid端口
- 使用SuperWebSocket实现Web消息推送
在大部分Web系统中,我们可能遇到需要向客户端推送消息的需求.SuperWebSocket第三方库能让我们轻松的完成任务.SuperWebSocket第三方库可以从网上下载,不过通过Visual St ...
- 一点资讯 视频抓取 phantomjs
# _*_ coding: utf- _*_ """ 思路: .列表页使用phantomjs模拟点击.每个链接只抓取第一页9-10条内容,按照标题去重 .布置定时任务,每 ...
- .Net Core 3.0 发布为单独的可执行文件
dotnet publish -r win-x64 -c Release /p:PublishSingleFile=true /p:PublishTrimmed=true