1. 程式人生 > >C#中控制執行緒池的執行順序

C#中控制執行緒池的執行順序

在使用執行緒池時,當用執行緒池執行多個任務時,由於執行的任務時間過長,會導制兩個任務互相執行,如果兩個任務具有一定的操作順序,可能會導制不同的操作結果,這時,就要將執行緒池按順序操作。下面先給一段程式碼,該程式碼是不按順序對執行緒池進行操作的,程式碼如下:

using System;

using System.Collections.Generic;

using System.Linq;

using System.Text;

using System.Threading;

namespace ConsoleApplication1

{

    class Program

    {

        static void Main(string[] args)

        {

            AutoResetEvent autoEvent = new AutoResetEvent(false);

            ThreadPool.QueueUserWorkItem(new WaitCallback(ThreadMethod), autoEvent);

            ThreadPool.QueueUserWorkItem(new WaitCallback(WorkMethod), autoEvent);

            Console.ReadLine();

        }

        static void ThreadMethod(object stateInfo)

        {

            for (int i = 0; i < 100;i++ )

                Console.WriteLine("ThreadOne, executing ThreadMethod, " + "is {0}from the thread pool.", Thread.CurrentThread.IsThreadPoolThread ? "" : "not ");

        }

        static void WorkMethod(object stateInfo)

        {

            for (int i = 0; i < 100; i++)

                Console.WriteLine("ThreadTwo, executing WorkMethod");

        }

    }

}

執行結果如圖1、圖2所示。

 

圖1  執行結果的上半部

 

圖2  執行結果的下半部

從圖1、圖2可以看出,在使用執行緒池對執行緒進行操作時,由於各任務的時間過長,多個任務的執行緒可能會互動操作,那麼,如何才能將執行緒池按指定的順序進行操作呢?主要是用AutoResetEvent類來實現的。

可以用AutoResetEvent類的WaitOne方法阻止執行緒,然後只執行當前操作的執行緒池,當遇到AutoResetEvent類的Set方法後,將當前執行緒設定為終止狀態,執行其他等待的執行緒。修改後的程式碼如下:

using System;

using System.Collections.Generic;

using System.Linq;

using System.Text;

using System.Threading;

namespace ConsoleApplication1

{

    class Program

    {

        static void Main(string[] args)

        {

            AutoResetEvent autoEvent = new AutoResetEvent(false);

            ThreadPool.QueueUserWorkItem(new WaitCallback(ThreadMethod), autoEvent);

            autoEvent.WaitOne();

            ThreadPool.QueueUserWorkItem(new WaitCallback(WorkMethod), autoEvent);

            autoEvent.WaitOne();

            Console.ReadLine();

        } 

        static void ThreadMethod(object stateInfo)
        {

            for (int i = 0; i < 100;i++ )

                Console.WriteLine("ThreadOne, executing ThreadMethod, " + "is {0}from the thread pool.", Thread.CurrentThread.IsThreadPoolThread ? "" : "not ");

            ((AutoResetEvent)stateInfo).Set();

        }
 
        static void WorkMethod(object stateInfo)

        {

            for (int i = 0; i < 100; i++)

                Console.WriteLine("ThreadTwo, executing WorkMethod");

            ((AutoResetEvent)stateInfo).Set();

        }

    }

}

執行結果如下: