CopyOnWriteArrayList 抛出 CurrentModificationException [英] CopyOnWriteArrayList throwing CurrentModificationException

查看:26
本文介绍了CopyOnWriteArrayList 抛出 CurrentModificationException的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

当我遍历一个列表时,我偶尔会收到一个 ConcurrentModificationException.谷歌搜索告诉我,这可能是因为我在迭代它的同时改变了另一个线程中的列表,为了解决这个问题,我应该使用 java.util.concurrent.CopyOnWriteArrayList....

I'm occasionally getting a ConcurrentModificationException when I iterate over a list. A Google search informs me that it's probably because I'm altering that list in another thread while iterating over it and that to make this problem go away I should use java.util.concurrent.CopyOnWriteArrayList....

...除了我已经是.

显然,我正在做一些真的愚蠢的事情.

Apparently, I'm doing something really stupid somewhere.

有人对如何诱导 CopyOnWriteArrayList 抛出 ConcurrentModificationException 有任何见解吗?如果重要的话,我使用的是 Java 5.

Does anybody have any insight into how one might induce CopyOnWriteArrayList to toss a ConcurrentModificationException? If it matters, I'm using Java 5.

由于我使用的修改器可能很重要,我将通过两种方式修改此列表:

Since the mutators I'm using may matter, I'm modifying this list in two ways:

  • 在前面添加元素.(list.add(0, newElement);)
  • 使用 subList 让旧项目从后面掉下来.(list = list.subList(0, MAX_LIST_SIZE);)

那些会引发危险信号吗?如果是这样,为什么?我的理解是,因为这些操作首先复制事物,任何现有的迭代器都将指向未修改的原始对象,因此不会在意.我的知识有漏洞吗?

Do those raise red flags? If so, why? My understanding was that because these operations make a copy of the thing first, any existing iterators would be pointing at the unmodified original and would thus not care. Do I have a hole in my knowledge?

编辑 2: 导致问题的确切代码仍然有点模糊,但我至少可以发布我看到的异常:

Edit 2: The precise code that's causing the problem is still a bit murky, but I can at least post the exception I'm seeing:


java.util.ConcurrentModificationException
    at java.util.concurrent.CopyOnWriteArrayList$COWSubList.checkForComodification(Unknown Source)
    at java.util.concurrent.CopyOnWriteArrayList$COWSubList.iterator(Unknown Source)
    at....

...它指向我代码中的 for-each 循环实例化.

... where it points to a for-each loop instantiation in my code.

那个 COWSubList 似乎暗示我对 subList 的调用是我问题的根源;我还是想知道为什么.

That COWSubList does seem to imply that my call to subList is the root of my problem; I'd still like to understand why.

编辑 3: *facepalm*

CopyOnWriteArrayList.subList() 返回一个 List不是一个 CopyOnWriteArrayList.它返回的列表没有提供任何 COWAL 保护的默示义务.这使得像这样使用 subList() 来删除元素是一个非常糟糕的主意.

CopyOnWriteArrayList.subList() returns a List, not a CopyOnWriteArrayList. The list it returns is under no implied obligation to provide any of COWAL's protections. Which makes using subList() like this to remove elements a Very Bad Idea.

不确定这是否是我的罪魁祸首,但这该死的可疑,无论如何都需要纠正.

Don't know for certain if this is my culprit, but it's damned suspicious and needs to be corrected regardless.

推荐答案

CopyOnWriteArrayList.subLists 抛出 ConcurrentModificationExceptions 如果包含列表从它下面改变:

CopyOnWriteArrayList.subLists throw ConcurrentModificationExceptions if the containing list changes out from underneath it:

public class ListTest {

  private static List<int[]> intList;

  public static void main (String[] args) {
    CopyOnWriteArrayList<Integer> cowal = new CopyOnWriteArrayList<Integer>();
    cowal.add(1);
    cowal.add(2);
    cowal.add(3);

    List<Integer> sub = cowal.subList(1, 2);
    cowal.add(4);
    sub.get(0); //throws ConcurrentModificationException
  }
}

这篇关于CopyOnWriteArrayList 抛出 CurrentModificationException的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆