近来在学习Eugene Agafonov编写的《C#多线程编程实战》(译),做些笔记也顺便分享一下^-^
AuotResetEvent类可以通知等待的线程有某件事发生~
using System; using System.Threading; namespace AuotResetEvent_Test { class Program { static void Main(string[] args) { var t = new Thread(() => Process(10)); t.Start(); Console.WriteLine("Waiting for another thread to complete work"); _workerEvent.WaitOne(); Console.WriteLine("First operation is completed!"); Console.WriteLine("Performing an operation on a main thread"); Thread.Sleep(TimeSpan.FromSeconds(5)); _mainEvent.Set(); Console.WriteLine("Now running the second operation on a second thread"); _workerEvent.WaitOne(); Console.WriteLine("Second operation is completed"); Console.ReadKey(); } private static AutoResetEvent _workerEvent = new AutoResetEvent(false); private static AutoResetEvent _mainEvent = new AutoResetEvent(false); static void Process(int seconds) { Console.WriteLine("Starting a long running work..."); Thread.Sleep(TimeSpan.FromSeconds(seconds)); Console.WriteLine("Work is done!"); _workerEvent.Set(); Console.WriteLine("Waiting for a main thread to complete its work"); _mainEvent.WaitOne(); Console.WriteLine("Starting second operation..."); Thread.Sleep(TimeSpan.FromSeconds(seconds)); Console.WriteLine("Work is done!"); _workerEvent.Set(); } } }
代码运行结果如下
当主程序启动时,定义了两个AutoResetEvent实例。其中一个是从子线程向主线程发信号,另一个实例是从主线程向子线程发信号。我们向AutoResetEvent构造方法中传入false,定义了这两个实例的初始状态为unsignaled。这意味着任何线程调用这两个对象中的任何一个WaitOne方法都将被阻塞,直到我们调用了Set方法。
然后我们创建了第二个线程,其会执行第一个操作10秒钟,然后等待从第二个线程发出的信号。该信号意味着第一个操作已经完成,现在第二个线程在等待主线程的信号。我们对主线程做了一些附加工作,并通过调用_mainEvent.Set方法发生一个信号,然后等待从第二个线程发出的另一个信号。
AutoResetEvent类采用的是内核时间模式,所以等待时间不能太长。使用ManualResetEvent类更好,因为它使用的是混合模式。