官术网_书友最值得收藏!

Using the ManualResetEventSlim construct

This recipe will describe how to make signaling between threads more flexible with the ManualResetEventSlim construct.

Getting ready

To step through this recipe, you will need Visual Studio 2015. There are no other prerequisites. The source code for this recipe can be found at BookSamples\Chapter2\Recipe5.

How to do it...

To understand the use of the ManualResetEventSlim construct, perform the following steps:

  1. Start Visual Studio 2015. Create a new C# console application project.
  2. In the Program.cs file, add the following using directives:
    using System;
    using System.Threading;
    using static System.Console;
    using static System.Threading.Thread;
  3. Below the Main method, add the following code:
    static void TravelThroughGates(string threadName, int seconds)
    {
      WriteLine($"{threadName} falls to sleep");
      Sleep(TimeSpan.FromSeconds(seconds));
      WriteLine($"{threadName} waits for the gates to open!");
      _mainEvent.Wait();
      WriteLine($"{threadName} enters the gates!");
    }
    
    static ManualResetEventSlim _mainEvent = new ManualResetEventSlim(false);
  4. Inside the Main method, add the following code:
    var t1 = new Thread(() => TravelThroughGates("Thread 1", 5));
    var t2 = new Thread(() => TravelThroughGates("Thread 2", 6));
    var t3 = new Thread(() => TravelThroughGates("Thread 3", 12));
    t1.Start();
    t2.Start();
    t3.Start();
    Sleep(TimeSpan.FromSeconds(6));
    WriteLine("The gates are now open!");
    _mainEvent.Set();
    Sleep(TimeSpan.FromSeconds(2));
    _mainEvent.Reset();
    WriteLine("The gates have been closed!");
    Sleep(TimeSpan.FromSeconds(10));
    WriteLine("The gates are now open for the second time!");
    _mainEvent.Set();
    Sleep(TimeSpan.FromSeconds(2));
    WriteLine("The gates have been closed!");
    _mainEvent.Reset();
  5. Run the program.

How it works...

When the main program starts, it first creates an instance of the ManualResetEventSlim construct. Then, we start three threads that wait for this event to signal them to continue the execution.

The whole process of working with this construct is like letting people pass through a gate. The AutoResetEvent event that we looked at in the previous recipe works like a turnstile, allowing only one person to pass at a time. ManualResetEventSlim, which is a hybrid version of ManualResetEvent, stays open until we manually call the Reset method. Going back to the code, when we call _mainEvent.Set, we open it and allow the threads that are ready to accept this signal to continue working. However, thread number three is still sleeping and does not make it in time. We call _mainEvent.Reset and we thus close it. The last thread is now ready to go on, but it has to wait for the next signal, which will happen a few seconds later.

There's more…

As in one of the previous recipes, we use a hybrid construct that lacks the possibility to work at the operating system level. If we need to have a global event, we should use the EventWaitHandle construct, which is the base class for AutoResetEvent and ManualResetEvent.

主站蜘蛛池模板: 旬邑县| 汤原县| 贵溪市| 宜兰市| 乌拉特前旗| 黎川县| 信丰县| 夏津县| 老河口市| 高台县| 化隆| 安新县| 双江| 壤塘县| 壤塘县| 揭西县| 横峰县| 偏关县| 抚顺市| 洛川县| 成安县| 和田县| 静安区| 庆城县| 胶南市| 鄂托克前旗| 鄂托克前旗| 贞丰县| 西乌珠穆沁旗| 临潭县| 姜堰市| 华阴市| 昆山市| 洱源县| 富锦市| 安顺市| 海伦市| 华容县| 长沙县| 共和县| 顺平县|