EventWaitHandle 第一课

本篇通过一个列子使用EventWaitHandle实现两个线程的同步。请参看下面的列子。

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;

namespace ThreadSynDemo
{
    class Program
    {
        private int n1, n2, n3;
        static void Main(string[] args)
        {
            Program p = new Program();
            Thread t0 = new Thread(new ThreadStart(p.WriteThread));
            Thread t1=new Thread(new ThreadStart(p.ReadThread));
            t0.Start();
            t1.Start();
            Console.ReadLine();
        }
        private void WriteThread()
        {
            Console.WriteLine("WriteThread");
            n1 = 1;
            n2 = 2;
            n3 = 3;
        }
        //有时结果为0+0+0=0;有时结果为1+2+3=6;因为线程执行循序是不确定性导致。
        //我们需要结果始终是1+2+3=6;这个需要保证WriteThread()比ReadThread()早执行。这个就涉及到线程的同步问题。

        private void ReadThread()
        {
            Console.WriteLine("{0}+{1}+{2}={3}",n1,n2,n3,n1+n2+n3);
        }
    }
}
上面的列子有时结果为0+0+0=0;有时结果为1+2+3=6;因为线程执行循序是不确定性导致。
我们需要结果始终是1+2+3=6;这个需要保证WriteThread()比ReadThread()早执行。这个就涉及到线程的同步问题。
下面我们就用EventWaitHandle实现这两个线程的同步。请看下面的列子:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
//下面我们使用EventWaitHandle类实现线程的同步
//EventWaitHandle类:能让操作系统通过发出的信号完成多个线程之间的同步,需要同步的线程可以阻塞当前线程。
//                   然后根据Windows操作系统发出的信号,决定阻塞等待其他工作完成,,还是不再等待而直接继续执行
//EventWaitHandle类方法如下:
//(1)Reset将信号的状态置为非终止状态(不让操作系统发出信号),从而导致那些只有收到信号才能继续执行的线程处于阻塞状态
//(2)Set:将事件状态置为终止状态,这样等待的线程会收到信号,从而有等待转为继续执行
//(3)WaitOne方法:阻塞当前线程,等待操作系统为其发出信号,直到收到信号才解除阻塞
//操作系统发出信号的两种方式:
//(1)发一个信号,使某个等待信号的线程解除阻塞,继续执行.自动重置(AutoResetEvent)
//(2)发一个信号,使所有等待信号的线程全部解除阻塞,继续执行.手动重置(ManualRestEvent)
namespace ThreadAsyDemo2
{
    class Program
    {
        private int n1, n2, n3;
        //将信号状态设置为非终止状态,使用手动重置
        EventWaitHandle myEventWaitHandle = new EventWaitHandle(false, EventResetMode.ManualReset);
        static void Main(string[] args)
        {
            Program p = new Program();
            Thread t0 = new Thread(new ThreadStart(p.WriteThread));
            Thread t1 = new Thread(new ThreadStart(p.ReadThread));
            t0.Start();
            t1.Start();
            Console.ReadLine();
        }
        private void WriteThread()
        {
            //允许其他需要等待的线程阻塞
            myEventWaitHandle.Reset();
            Console.WriteLine("WriteThread");
            n1 = 1;
            n2 = 2;
            n3 = 3;
            //允许其他等待的线程继续
            myEventWaitHandle.Set();
        }
        //有时结果为0+0+0=0;有时结果为1+2+3=6;因为线程执行循序是不确定性导致。
        //我们需要结果始终是1+2+3=6;这个需要保证WriteThread()比ReadThread()早执行。这个就涉及到线程的同步问题。

        private void ReadThread()
        {
            //阻塞当前线程,直到收到信号
            myEventWaitHandle.WaitOne();
            Console.WriteLine("{0}+{1}+{2}={3}", n1, n2, n3, n1 + n2 + n3);
        }
    }
}
转载至:https://www.cnblogs.com/Joetao/articles/3152497.html

原文地址:https://www.cnblogs.com/jshchg/p/11666213.html