问题:

我试图从 ThreadPool 中抛出 6 个线程来处理单个任务。每个任务的 ManualResetEvent 都存储在一个手动重置事件数组中。线程数对应于 ManualResetEvent Array 中的索引。

现在发生的情况是,一旦我启动了这 6 个线程,我就会移出并等待线程完成。线程的等待是在主线程中完成的。

现在有时发生的情况是我的等待逻辑即使在很长时间(我见过的 2 天)之后也不会返回。这是线程等待逻辑的代码示例

                foreach (ManualResetEvent whandle in eventList)
                {
                    try
                    {
                        whandle.WaitOne();
                    }
                    catch (Exception) { }
                }

根据 .WaitOne 的文档。如果未从线程接收到 Set 事件,则同步调用使线程不返回。

有时我的线程的工作量较少,它们甚至可能在我到达等待逻辑之前返回。 .WaitOne() 是否有可能等待 Set() 事件,即使它在过去收到过?
这是等待所有线程关闭的正确逻辑吗?

最佳答案

我不直接回答这个问题。这是你应该做的:

使用 Task.Factory.StartNew 启动任务并使用 Task.WaitAll(Task[]) 等待它们。您不必以这种方式处理事件。异常将很好地传播到“ fork ”线程。您不再需要旧的 ThreadPool API。

希望这可以帮助。

关于c# - ManualResetEvent 的可能竞争条件,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/16122051/

10-09 05:14