如何在使用 for-each 循环迭代时修改 Collection 而不会出现 ConcurrentModificationException?

发布于 2024-11-27 21:44:12 字数 81 浏览 3 评论 0原文

如果我在使用 for-each 循环迭代集合时修改集合,则会给出 ConcurrentModificationException。有什么解决方法吗?

If I modify a Collection while iterating over it using for-each loop, it gives ConcurrentModificationException. Is there any workaround?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

刘备忘录 2024-12-04 21:44:12

使用 Iterator#remove

这是在迭代期间修改集合的唯一安全方法。有关详细信息,请参阅集合接口教程。

如果您还需要在迭代时添加元素的能力,请使用ListIterator.

Use Iterator#remove.

This is the only safe way to modify a collection during iteration. For more information, see The Collection Interface tutorial.

If you also need the ability to add elements while iterating, use a ListIterator.

栩栩如生 2024-12-04 21:44:12

一种解决方法是保存更改并在循环后添加/删除它们。

例如:

List<Item> toRemove = new LinkedList<Item>();

for(Item it:items){
    if(remove){
        toRemove.add(it);
    }
}
items.removeAll(toRemove);

One work around is to save your changes and add/remove them after the loop.

For example:

List<Item> toRemove = new LinkedList<Item>();

for(Item it:items){
    if(remove){
        toRemove.add(it);
    }
}
items.removeAll(toRemove);
踏雪无痕 2024-12-04 21:44:12

第二种解决方法是使用其迭代器不会给出异常的集合类。例如 ConcurrentLinkedQueue< /a>, ConcurrentHashMap 等等。

这些通过为迭代器提供较弱的一致性模型来避免抛出异常。 (当然,您需要了解这些模型,并确定它们是否适合您的应用程序。)

它们通常比非并发集合慢一点,但如果存在严重争用,则比同步集合包装器快。

A second workaround is to use a collection class whose iterators won't give the exception. For example ConcurrentLinkedQueue, ConcurrentHashMap and so on.

These avoid the need to throw exceptions by providing weaker models of consistency for the iterators. (Of course, you need to understand those models, and decide whether they are suitable for your application.)

They are typically a bit slower than non-concurrent collections, but faster than the synchronized collection wrappers if there is significant contention.

岁吢 2024-12-04 21:44:12

如果只想从集合中删除元素,可以使用 Iterator 而不是 Iterable。

否则,您可以做的不是迭代原始集合,而是首先复制列表。例如,如果您的集合是一个列表,那么您可以创建一个新的 ArrayList(originaList) 并对其进行迭代。修改应在原始列表的基础上进行。

另一种可能更适合您的用例的替代方案是不使用 for-each 而是使用传统的 for-。

If you just want to remove the element from the collection, you can use Iterator instead of Iterable.

Otherwise, what you can do is not to iterate the original collection, but first make a copy of the list. For example if your collection is a list, than you can make a new ArrayList(originaList) and iterate over that. The modification should be done to the original list.

Another alternative which maybe better for your use case, is not to use for-each but the traditional for-.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文