如果在获得了某个集合的迭代器之后,除了通过这个迭代器之外对该集合做了结构性的修改(添加元素或删除元素),那么再调用这个迭代器的next()或remove()方法就会抛ConcurrentModificationException异常。
代码如:
写道
ArrayList<Integer> list1 = new ArrayList<Integer>(Arrays.asList(1));
Iterator<Integer> list1_iterator1 = list1.iterator();
list1.add(2);
list1_iterator1.next();// 此处会抛ConcurrentModificationException
又如:
写道
ArrayList<Integer> list2 = new ArrayList<Integer>(Arrays.asList(1));
Iterator<Integer> list2_iterator1 = list2.iterator();
Iterator<Integer> list2_iterator2 = list2.iterator();
list2_iterator1.next();
list2_iterator1.remove();
list2_iterator2.next();// 此处会抛ConcurrentModificationException
同样,对Collections.synchronized**()方法返回的线程安全集合类在进行迭代时,发生了上述情况也会抛ConcurrentModificationException。
代码如:
写道
package ConcurrentModificationException;
import java.util.Iterator;
import java.util.List;
/**
* 此任务对迭代器代表的集合做了结构性更改
*/
public class Iterator1 implements Runnable {
private Iterator<Integer> iterator;
private List<Integer> synchronizedList;
public Iterator1(Iterator<Integer> iterator, List<Integer> synchronizedList) {
this.iterator = iterator;
}
@Override
public void run() {
System.out.println("Iterator1 run");
iterator.next();
iterator.remove();
}
}
package ConcurrentModificationException;
import java.util.Iterator;
import java.util.List;
/**
* Iterator1对迭代器代表的集合做了结构性更改
*/
public class Iterator2 implements Runnable {
private Iterator<Integer> iterator;
private List<Integer> synchronizedList;
public Iterator2(Iterator<Integer> iterator, List<Integer> synchronizedList) {
this.iterator = iterator;
}
@Override
public void run() {
System.out.println("Iterator2 run");
iterator.next(); //此处会抛ConcurrentModificationException
}
}
package ConcurrentModificationException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.Iterator;
import java.util.List;
public class Main {
public static void main(String[] args) {
ArrayList<Integer> list2 = new ArrayList<Integer>(Arrays.asList(1));
final List<Integer> synchronizedList = Collections.synchronizedList(list2);
Iterator<Integer> iterator1 = synchronizedList.iterator();
Iterator<Integer> iterator2 = synchronizedList.iterator();
Thread t1 = new Thread(new Iterator1(iterator1, synchronizedList));// 线程1对迭代器代表的集合(synchronizedList)做了结构性更改
Thread t2 = new Thread(new Iterator2(iterator2, synchronizedList));
t1.start();
t2.start();
}
}
在
HashMap
的
API
中指出:
由所有
HashMap
类的
“collection
视图方法
”
所返回的迭代器都是快速失败的:在迭代器创建之后,如果从结构上对映射进行修改,除非通过迭代器本身的
remove
方法,其他任何时间任何方式的修改,迭代器都将抛出
ConcurrentModificationException
。因此,面对并发的修改,迭代器很快就会完全失败,而不冒在将来不确定的时间发生任意不确定行为的风险。
注意,迭代器的快速失败行为不能得到保证,一般来说,存在非同步的并发修改时,不可能作出任何坚决的保证。快速失败迭代器尽最大努力抛出
ConcurrentModificationException
。因此,编写依赖于此异常的程序的做法是错误的,正确做法是:迭代器的快速失败行为应该仅用于检测程序错误。
分享到:
相关推荐
java.util.ConcurrentModificationException 异常问题详解1
NULL 博文链接:https://chenlinbo.iteye.com/blog/832335
主要介绍了出现java.util.ConcurrentModificationException 问题及解决办法的相关资料,需要的朋友可以参考下
java.util.ConcurrentModificationException 解决方法 在使用iterator.hasNext()操作迭代器的时候,如果此时迭代的对象发生改变,比如插入了新数据,或者有数据被删除。 则使用会报以下异常: Java.util....
今天小编就为大家分享一篇关于Java源码解析ArrayList及ConcurrentModificationException,小编觉得内容挺不错的,现在分享给大家,具有很好的参考价值,需要的朋友一起跟随小编来看看吧
axis1.4补丁包,解决jdk1.8高并发报ConcurrentModificationException问题,该jar包重新编译jar包的一个class文件,线上环境通过
Spring数据mongodb测试 在Collections.synchronizedList或Collections.synchronizedSet上测试spring数据mongodb ConcurrentModificationException
Map在遍历时候通常 现获得其键值的集合Set,然后用迭代器Iterator来对Map进行遍历。
java.util.ConcurrentModificationException: mutation occurred during iteration [error] scala.collection.mutable.MutationTracker$.checkMutations(MutationTracker.scala:43) [error] scala.collection....
axis1.4 spring3.0 集成 实现 web service 服务端, axis1.4 客户端认证,授权,访问日志记录,集成spring 解决 PHP 调用web service 无法认证,和解析soap 模板
fastJson的全部资料,包括源码、开发需要用到的jar包和html格式的文档。
这里面包含了大部分的软件测试的专业术语,希望对你有用
ArithmeticException, ArrayStoreException, BufferOverflowException, BufferUnderflowException, CannotRedoException, CannotUndoException, ClassCastException, CMMException, ConcurrentModificationException,...
ConcurrentModificationException异常 线程安全的集合 线程安全的 List CopyOnWriteArrayList 线程安全的Set 线程安全的Map ConcurrentHashMap ConcurrentSkipListMap java集合 线程不安全的集合 HashMap的特点 ...
3、在使用 project.tasks.withType()时,Gradle 4.8 有时会失败,并抛出 ConcurrentModificationException 。 4、依赖关系解析引擎有时会抛出 “Unexpected parent dependency” 报错,这在 Gradle 4.8 中变得更加...
3. 迭代过程中,即使Map结构被修改,也不会抛ConcurrentModificationException异常; 4. 除了数组+链表+红黑树的基本结构外,新增了转移节点,是为了保证扩容时的线程安全的节点; 5. 提供了很多Stream流式方法,...
避免在循环中修改集合,可能导致ConcurrentModificationException。 异常处理: 不要忽视异常,合理捕获并处理它们。 不要过度使用try-catch,应尽量抛出业务异常给上层处理。 使用finally块进行资源清理。 并发...
只读迭代:由于写时复制的机制,CopyOnWriteArraySet 的迭代器是只读的,即迭代过程中不会抛出 ConcurrentModificationException 异常。但是,迭代器获得的数据可能不包含最新的修改。 较高的内存占用:由于每次...