c#线程同步-自动恢复事件

c#线程同步-自动恢复事件,c#,.net,multithreading,C#,.net,Multithreading,我一直在使用AutoResetEvent在线程之间进行同步 一些线程(A-F)调用autoresetevent.WaitOne();在等待另一个线程(X)完成其工作时 当拥有autoresetevent的线程(X)执行其工作并调用.Set()时 但是,只有一个等待线程(A-F)未被阻止。-当线程(X)完成它的工作时,我如何让它们全部解除阻塞 我猜我使用了错误的同步原语-我应该使用什么以及如何使用 代码示例将是理想的您正在寻找的是什么 它将保持设置,直到被某个线程重置 在代码的某个地方,您必须

我一直在使用AutoResetEvent在线程之间进行同步

  • 一些线程(A-F)调用autoresetevent.WaitOne();在等待另一个线程(X)完成其工作时
  • 当拥有autoresetevent的线程(X)执行其工作并调用.Set()时
但是,只有一个等待线程(A-F)未被阻止。-当线程(X)完成它的工作时,我如何让它们全部解除阻塞

我猜我使用了错误的同步原语-我应该使用什么以及如何使用

代码示例将是理想的

您正在寻找的是什么

它将保持设置,直到被某个线程重置


在代码的某个地方,您必须知道何时重置它。这可能是一个简单的计数器或派生线程的集合。

使用System.Threading.ManualResetEvent

线程A-F调用
mre.WaitOne()
等待线程(X)

当线程X结束时,调用
mre.Set()
将唤醒线程A-F


在线程X中,通过执行
mre.reset()
将mre重置为基本状态,假设您有以下代码:

class Program
{
    static void Main(string[] args)
    {
        var are = new AutoResetEvent(false);

        for (int i = 0; i < 10; i++)
        {
            var j = i;
            new Thread(() =>
            {
                Console.WriteLine("Started {0}", j);
                are.WaitOne();
                Console.WriteLine("Continued {0}", j); 
            }).Start();
        }

        are.Set();

        Console.ReadLine();
    }
}
但如果你改为使用:


当然,顾名思义,
ManualResetEvent
需要手动重置,而
AutoResetEvent
会在第一个
WaitOne
释放其线程后自动重置

听起来您也想同步A-F线程。更多信号或ManualResetEvent+联锁计数器可能会工作。问题是我不知道a-F中有多少线程,所以我无法调用设置正确的时间数。您在寻找什么?@Ani我将如何使用monitor.pulsell?它会比下面提到的MaulalReSeTebug更好吗?你应该考虑阅读RealWrordLoxsLimaHA!听起来不错!“当控制线程完成活动时,它会调用Set来表示等待的线程可以继续。所有等待的线程都会被释放。”我来试试!是的,就是这样:)不知道为什么选择手动和自动名称,它们不是很有描述性:)自动自动重置,手动需要显式或手动操作来设置事件。我很高兴它成功了。在这个链接中有一个更好的ManualResetEvent示例/描述:感谢代码示例(+1),这就是我正在体验的问题和解决方案。第一个接受了Emo。还是不知道这两个类的名称!请注意,Markus Johnsson没有调用mre.Reset()(执行手动重置)。你可能想这样做。
Started 0
Started 1
Started 2
Started 3
Started 4
Started 5
Started 6
Started 7
Started 8
Continued 0
Started 9
class Program
{
    static void Main(string[] args)
    {
        var mre = new ManualResetEvent(false);

        for (int i = 0; i < 10; i++)
        {
            var j = i;
            new Thread(() =>
            {
                Console.WriteLine("Started {0}", j);
                mre.WaitOne();
                Console.WriteLine("Continued {0}", j); 
            }).Start();
        }

        mre.Set();

        Console.ReadLine();
    }
}
Started 0
Started 1
Started 2
Started 3
Started 4
Started 5
Started 6
Started 7
Started 8
Started 9
Continued 1
Continued 8
Continued 7
Continued 4
Continued 5
Continued 6
Continued 3
Continued 0
Continued 9
Continued 2