C#線程池的代碼
sealed class MyThreadPool { //線程鎖對象 private static object lockObj = new object(); //任務隊列 private static Queue<ThreadStart> threadStartQueue = new Queue<ThreadStart>(); //記錄當前工作的任務集合,從中可以判斷當前工作線程使用數,如果使用int判斷的話可能會有問題, //用集合的話還能取得對象的引用,比較好 private static HashSet<ThreadStart> threadsWorker = new HashSet<ThreadStart>(); //當前允許最大工作線程數 private static int maxThreadWorkerCount = 1; //當前允許最小工作線程數 private static int minThreadWorkerCount = 0; /// <summary> /// 設定最大工作線程數 /// </summary> /// <param name="maxThreadCount">數量</param> public static void SetMaxWorkThreadCount(int maxThreadCount) { maxThreadWorkerCount = minThreadWorkerCount > maxThreadCount ? minThreadWorkerCount : maxThreadCount; } /// <summary> /// 設定最小工作線程數 /// </summary> /// <param name="maxThreadCount">數量</param> public static void SetMinWorkThreadCount(int minThreadCount) { minThreadWorkerCount = minThreadCount > maxThreadWorkerCount ? maxThreadWorkerCount : minThreadCount; } /// <summary> /// 啟動線程池工作 /// </summary> /// <param name="threadStartArray">任務數組</param> public static void MyQueueUserWorkItem(List<ThreadStart> threadStartArray) { //將任務集合都放入到線程池中 AddAllThreadsToPool(threadStartArray); //線程池執行任務 ExcuteTask(); } /// <summary> /// 將單一任務加入隊列中 /// </summary> /// <param name="ts">單一任務對象</param> private static void AddThreadToQueue(ThreadStart ts) { lock (lockObj) { threadStartQueue.Enqueue(ts); } } /// <summary> /// 將多個任務加入到線程池的任務隊列中 /// </summary> /// <param name="threadStartArray">多個任務</param> private static void AddAllThreadsToPool(List<ThreadStart> threadStartArray) { foreach (var threadStart in threadStartArray) AddThreadToQueue(threadStart); } /// <summary> /// 執行任務,判斷隊列中的任務數量是否大于0,如果是則判斷當前正在使用的工作線程的 /// 數量是否大于等于允許的最大工作線程數,如果一旦有線程空閑的話 /// 就會執行ExcuteTaskInQueen方法處理任務 /// </summary> private static void ExcuteTask() { while (threadStartQueue.Count > 0) { Thread.Sleep(100); if (threadsWorker.Count < maxThreadWorkerCount) { ExcuteTaskInQueen(); } } } /// <summary> /// 執行出對列的任務,加鎖保護 /// </summary> private static void ExcuteTaskInQueen() { lock (lockObj) { ExcuteTaskByThread( threadStartQueue.Dequeue()); } } /// <summary> /// 實現細節,這里使用BackGroudWork來實現后臺線程 /// 注冊doWork和Completed事件,當執行一個任務前,前將任務加入到 /// 工作任務集合(表示工作線程少了一個空閑),一旦RunWorkerCompleted事件被觸發則將任務從工作 /// 任務集合中移除(表示工作線程也空閑了一個) /// </summary> /// <param name="threadStart"></param> private static void ExcuteTaskByThread(ThreadStart threadStart) { threadsWorker.Add(threadStart); BackgroundWorker worker = new BackgroundWorker(); worker.DoWork += (o, e) => { threadStart.Invoke(); }; worker.RunWorkerCompleted += (o, e) => { threadsWorker.Remove(threadStart); }; worker.RunWorkerAsync(); } }
本文由用戶 cymt 自行上傳分享,僅供網友學習交流。所有權歸原作者,若您的權利被侵害,請聯系管理員。
轉載本站原創文章,請注明出處,并保留原始鏈接、圖片水印。
本站是一個以用戶分享為主的開源技術平臺,歡迎各類分享!