1. 程式人生 > 其它 >C# 多執行緒實踐 -- 執行緒間訊號通知

C# 多執行緒實踐 -- 執行緒間訊號通知

使用ManualResetEvent 在一個執行緒中控制另一個執行緒的執行

首先需要先例項化一個訊號物件 ManualResetEvent signal= new ManualResetEvent(false);

signal.WaitOne() 阻塞當前執行緒,等待接收到其他執行緒發來的取消訊號
signal.Set() 傳送取消阻塞訊號, 取消成功返回true,失敗返回false
signal.Reset() 傳送再次阻塞訊號,阻塞成功返回true,失敗返回false

public partial class Form2 : Form
    {
        // 執行緒間訊號,在一個執行緒中呼叫WaitOne方法阻塞等待,直到收到訊號
        // 另一個執行緒中使用Set方法傳送訊號
        ManualResetEvent signal;

        public Form2()
        {
            InitializeComponent();
            signal = new ManualResetEvent(false);

            new Thread(Test1).Start();

            new Thread(Test2).Start();
        }

        public void Test1()
        {
            while (true)
            {
                signal.WaitOne();// 阻塞當前執行緒,直到等到訊號
                Console.WriteLine("收到訊號");
                Thread.Sleep(100);
            }
        }

        public void Test2()
        {
            int i = 0;
            while(i< 3)
            {
                i++;
                Console.WriteLine(i);
                Thread.Sleep(1000);
            }

            Console.WriteLine("等待結束");

            signal.Set(); // 取消阻塞
           
            signal.Reset(); // 再次阻塞
        }

    }

使用CancellationTokenSource發起取消執行緒繼續執行請求訊號

/*
     * 場景:當主執行緒開闢了一個子執行緒去執行一個耗時的操作,執行了一段時間還沒結束,這時主執行緒等不及了,於是就發出申請
     * 取消子執行緒繼續執行,就是告訴子執行緒你可以結束了。
     */
    public partial class CancellationTokenForm : Form
    {
        // 建立token
        CancellationTokenSource cts = new CancellationTokenSource();

        public CancellationTokenForm()
        {
            InitializeComponent();

            Task.Run(Test);
        }

        void Test()
        {
            while (true)
            {
                // 外部發出取消繼續執行當前執行緒的請求
                if (cts.IsCancellationRequested)
                {
                    break;
                }

                Console.WriteLine("等待中...");
                Thread.Sleep(500);
            }

            Console.WriteLine("等待結束");
        }

        private void button1_Click(object sender, EventArgs e)
        {
            // 發出取消繼續執行執行緒的申請
            cts.Cancel();
        }
    }