【问题标题】:How to substitute at runtime the WaitHandle that a thread should wait on如何在运行时替换线程应该等待的 WaitHandle
【发布时间】:2011-02-18 09:40:33
【问题描述】:

我想知道如何在运行时安全地更改线程应该等待的 EventWaitHandle。

假设有两个线程(A 和 C)通过 EventWaitHandles 同步。 A 循环地完成它的工作,C 等待直到它收到来自 A 的通知,它可以开始做它的工作(例如,通过 AutoResetEvent)。模式是A-C-A-C...

稍后在启动新线程 (B) 时(例如,通过用户操作),它的作业应该以这种方式在两个预先存在的线程之间执行:A 完成它的工作,然后向 B 发出信号,一旦 B 完成它就向 C 发出信号. 现在模式是ABCABC...

所以在线程 C 等待与 A 共享的 EventWaitHandle 之前,应该有一个安全机制使 C 等待与 B 共享的另一个 EventWaitHandle。在我看来,棘手的部分是替换 C 使用的 EventWaitHandle,因为一旦完成,我应该能够轻松地启动 B,它将使用 EventWaitHandle 等待 A 作业和 EventWaitHandle 发出 C 作业的信号。该机制还应该提供一种安全卸载线程 B 并返回到只有线程 A 和 C 正在工作的初始情况的方法。

有没有一种安全的方法可以使用 EventWaitHandle 来完成此任务?如果没有,任何其他建议将不胜感激。

【问题讨论】:

  • 如果您使用的是 .NET 4.0,那么使用 Tasks 会更简单。本质上,您将拥有三个任务,使得 A“继续”B 和 B“继续”C。B 在无事可做的情况下基本上什么都不做,但在有事时会做某事。而不是试图从混合中“插入”和“移除”B,它可以/应该总是在混合中。这将使所有这一切变得不那么难以维护。

标签: c# multithreading waithandle


【解决方案1】:

如果任务 A 知道更改,则让任务 C 拥有该事件。任务 A 通知任务 C 的事件,如果 C 是下一个,或者任务 B 的事件,如果任务 B 是下一个。

或者,使用与更改任何其他共享数据相同的机制:在对句柄的所有访问中获取互斥锁。例如任务 C 获取锁,读取句柄,释放锁,等待句柄。要更改它,您需要 UI 线程获取锁、更改句柄、释放锁。

【讨论】:

  • 谢谢我尝试了你的第二个选择,它奏效了。但是换了把手,在获得锁之前,我必须用信号通知前一个把手以避免死锁
【解决方案2】:

您是否考虑过实现某种调度程序,其中线程可以使用句柄注册(取消注册)以启动和发出完成信号。然后调度程序通过设置适当的启动事件来启动下一个线程,并在前一个线程设置完成事件时继续下一个线程。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-10-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多