【问题标题】:Is there a list collection supporting concurrent modification while iterating? [closed]迭代时是否有支持并发修改的列表集合? [关闭]
【发布时间】:2014-01-10 22:01:09
【问题描述】:

是否有实现 List 接口的容器,支持在迭代时并发修改?具体来说,我希望一个线程迭代集合,而许多线程从这个列表中插入和删除元素。迭代器应该看到对它尚未遍历的列表的修改。

我正在寻找类似于 ConcurrentLinkedQueue 但支持在特定索引处添加和删除元素的迭代行为。最好我正在寻找强一致性(并且愿意为此支付锁争用开销),但我可能会忍受弱一致性。

我很高兴看到第三方库,因为我在标准库中看不到任何提供我正在寻找的东西的东西。

【问题讨论】:

  • 抱歉,我不知道这是题外话。我的本意不是征求意见,而是要发现是否存在适合我需要的东西。

标签: java list collections concurrency iteration


【解决方案1】:

附近有东西。它被称为 CopyOnWriteArrayList - 尽管存在的限制是迭代器在迭代时不会看到所做的更改,而是会像迭代开始时一样继续迭代集合。

Collection 的写入速度很慢(但读取速度很快),这是另一件需要考虑的事情。

jME3 有一个名为SafeArrayListdoc here 的内部集合,速度更快,但不支持多线程访问。它确实支持从迭代器等访问(因此您可以遍历列表中的对象并同时从中添加/删除它们,只要您不尝试从多个线程中执行此操作)。同样,迭代器在迭代时不会看到所做的更改,它们将继续迭代原始数据。

并发包提供了许多其他数据结构也可能有所帮助。

另一种方法是仅使用列表中的标准ArrayListsynchronize 进行修改和读取,然后使用索引对其进行迭代。 (即list.get(i))。

虽然会有很多边缘情况。例如,如果您删除一个元素,它会将所有其他元素向下移动,因此您将在超过该点的任何迭代器上跳过一个。

事实上,您最终可能需要保留一个迭代器列表,当您添加/删除元素时,循环遍历您的迭代器列表并相应地更新它们的位置!

【讨论】:

    【解决方案2】:

    单独使用 Java API,您可以使用Collections.synchronizedList() 获取同步列表。检查方法的规范是否适合您的使用。并且,使用ListIterator(使用List.listIterator()方法获得)来迭代和修改列表。

    【讨论】:

    • 那不行,它会在迭代时锁定列表以进行修改。
    • 但是为写入锁定集合应该还是可以的,不是吗?
    • 他想要一个迭代器,它可以在迭代时看到所做的更改。如果集合被锁定,他们将无法进行更改...
    猜你喜欢
    • 2013-05-13
    • 2017-12-05
    • 2015-09-07
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-11-24
    • 2014-09-17
    相关资源
    最近更新 更多