【问题标题】:Concurrent Queue Data Structure with ArrayList as Element以 ArrayList 为元素的并发队列数据结构
【发布时间】:2019-10-18 13:07:37
【问题描述】:

细节问题

在使用数据结构时是否会导致任何问题,例如ArrayBlockingQueue<ArrayList<MyClass>>
多线程?

背景

在高层次上,我正在努力实现我有一个制作人来制作一个巨大的列表。为了加快处理速度。我决定使用多个消费者(线程)来消费生产者产生的巨大列表。

我的建议解决方案

我会将巨型列表转换为多个相对较小的列表,为了确保其线程安全,我会将这些较小的列表排入并发数据结构。因此,在多线程场景中,每个线程只需轮询并发队列以获取一个列表并对其进行处理。

问题陈述

在多线程场景中,我知道我们必须使用并发数据结构来避免线程干扰并建立happens-before关系。

  • 但是使用非线程安全的数据结构作为线程安全数据结构的元素会安全吗?

  • 在使用数据结构时会导致任何问题,例如ArrayBlockingQueue<ArrayList<MyClass>>
    有多个线程?

  • 对性能有影响吗?

【问题讨论】:

  • 欢迎任何帮助/建议!
  • 您是否考虑过将单个 MyClass 元素逐个排入队列?也许你的制作人不需要这样建立庞大的列表?
  • @Thilo 。感谢您提出此解决方案。对于我的用例,我将只有有限数量的线程作为消费者。因此,即使将个人 `MyClass` 排入队列,它会降低性能吗?并发数据结构内部使用可重入锁,可能一个线程在短时间内阻塞另一个线程。所以如果我使用`ConcurrentQueue>`,那么我可以减少不同线程和共享变量之间的交互。

标签: java multithreading concurrency thread-safety


【解决方案1】:

这种方法应该没有明显的问题。

使用非线程安全数据结构作为线程安全数据结构的元素会安全吗?

只要您正确协调(或避免)对非线程安全的内部数据结构的并发访问,这是安全的。 ArrayBlockingQueue 确保在您通过peekpoll 或相关方法访问其元素时建立happens-before 关系。

在使用多线程数据结构(例如ArrayBlockingQueue<ArrayList<MyClass>>)时会导致任何问题吗?

不,这就是BlockingQueue 的用途,只要您协调对内部列表的访问(见上文)。

对性能有影响吗?

一般来说,单个生产者将列表划分为子列表的方法可能不是最佳的。生产者不/不应该知道消费者的数量及其带宽,因此通常不知道哪些分区大小可以正常工作。更好的方法可能是使用ArrayBlockingQueue<MyClass>,并且从消费者端始终通过调用drainTo 来获取合适数量的maxElements 元素来一次性消耗多个元素。

【讨论】:

  • 感谢您的 cmets。所以简短的回答是 1. 如果我使用 drainTo 到一个新列表并开始处理它不会有任何问题。 2.性能完全不会受到影响,因为每个线程都有自己的列表,因为它们正在处理单个线程进程。我理解正确吗?
  • 谢谢。完成此项目后,我将更新我的问题。 :)
【解决方案2】:

感谢 michid@ 和 Thilo@ 的回答

最终分辨率

我最终使用LinkedBlockingQueue<List<MyObjClass>> 并有多个子线程从队列中轮询。每个子线程将获取MyObjClass 的列表来处理。

此分辨率不会降低性能。
为什么我选择LinkedBlockingQueue 而不是ArrayBlockingQueue 请参阅Link

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-10-27
    • 2015-09-17
    • 1970-01-01
    相关资源
    最近更新 更多