7

我有一个递归问题,消费者在树的每一层都做了一些工作,然后需要沿着树递归并在下一层执行相同的工作。

我想使用 ConcurrentBag/BlockingCollection 等来并行运行它。在这种情况下,队列的消费者,也是队列的生产者!

我的问题是这样的:使用 BlockingCollection,我可以编写非常简单的 foreach 逻辑来使项目出队,并将新项目排队 - 当队列为空时,阻塞集合将正确阻塞,并等待另一个产生新工作消费者。

但是我怎么知道是否所有的消费者都在阻止?!

我知道 CompleteAdding(),但这似乎没有用,因为你真正完成的唯一时间是所有生产者都完成生产并且队列为空 - 因为它们都会阻塞,所以没有人“ free" 来设置 CompleteAdding()。有没有办法检测到这一点?(也许一个事件可以在阻塞时触发,并在解除阻塞时再次触发?)

我可以手动处理这个问题,不使用 foreach,而是手动使用 while(!complete) 循环,并使用 TryTake,但是我需要手动休眠,这似乎效率低下(拥有阻塞集合的全部原因与只是首先是并发集合!)每次通过循环,如果 TryTake 为 false,我可以设置一个 Idle 标志,然后让 Master 检查队列是否为空,并且所有线程都处于空闲状态,设置一个完整标志,但是,这似乎很笨拙。

直觉告诉我有一些方法可以使用阻塞收集来做到这一点,但我无法做到。

无论如何,当消费者是生产者并且能够检测到何时释放所有块时,任何人都有一个很好的模式会很棒

4

0 回答 0