1. 先看两段代码
这段代码在执行的时候会报
但是这样写就好着呢:
总结, 研究报错的代码 , 在 for 循环的时候调用 next() 方法, next 方法中调用了 checkForComodification 这个方法, 这个方法里面判断 modCount 和 expectedModCount 不相等的时候就抛出 ConcurrentModificationException 这个异常.
原因: 当 for 循环执行的时候首先调用了
这个方法, 这个方法初始化了 expectedModCount=modCount,modCount 的值是在 add 方法里面复制的, 如当前程序为 8, 初始化给 expectedModCount 的值. 当调用 remove 方法的时候, 将 modCount++; 导致下一次循环的时候两个值不相同, 就会报这个错误.
这里还有个知识点:
modCount 这个变量被 transient 关键字修饰, 意思是不可被序列化.
参考文档: https://www.cnblogs.com/chenpi/p/6185773.html
2. 解决办法:
- for (int i = students.size() - 1; i>= 0; i--) {
- if (students.get(i).equals("李四")) {
- students.remove(i);
- }
- }
注意倒叙删除. 正序删除的时候由于 size 一直变小, 可能后面的删除不了.
- Iterator<String> iterator = students.iterator();
- while (iterator.hasNext()) {
- if (iterator.next().equals("李四"))
- iterator.remove();
- }
用 iterator 的 remove 方法可以删除, 因为 remove 方法中将 expectedModCount=modCount.
2. 多线程问题
这段代码在执行的时候有时候会报错, 就是在方法内部调用 next 方法的时候 expectedModCount 和 modCount 的值不一致引起的.
解决方案:
用 CopyOnWriteArrayList 方法, 注意这个方法没有实现 iterator.remove().CopyOnWriteArrayList 里面在操作数据都用 Lock 进行了处理, 但是有个方法 getArray() 没有 lock.
3. ConcurrentHaspMap 它也是线程安全的, 它里面是通过 synchronized 实现的.
来源: https://www.cnblogs.com/baoyi/p/java_arrayList.html