一个用来“拉”任务的简单线程池 c#版

通常用到线程池时,会用到“生产者-消费者”模型。

如果项目中不好实现“生产者”这一角色,而是预先开好N条线程,然后让线程自己去“拉”任务,“拉”到有任务就处理,然后再“拉”任务,这样实现起来很简单,但任务的源头若是一直没有任务,这N条线程依然是不停地在“拉”,消耗着CPU资源。于是想出了以下方案:

开好N条线程

1.第一条线程在循环“拉”任务,其他的在阻塞(这样就不占CPU资源了)。

2.直到第一条线程拉到有任务,先“告诉”其他线程:我有活干了,你们谁有空的去“源头”把风,有活你们接着干。

3.其中一条线程站了出来(简称第二条),同样是循环“拉”任务,如果此时“源头”还有任务,第二条线程同样先“告诉”其他还在阻塞的线程,自己然后干活。

4.第三条站了现来,不停在循环“拉”任务。

5.第一和第二条干完活了,变成了阻塞状态,等通知(此时在把风的线程)。

照着这样的思路,用C#写了以下模型,不知.NET库里是否有现成的,若有,就当学习吧

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

namespace testMutex
{
    class Program
    {
        int threadPollMaxNUM = 3;   //最大线程数
        Thread thread3;
        Mutex mutex;
        object lockObject = new object();

        public Program()
        {
            mutex = new Mutex();
        }

        static void Main(string[] args)
        {
            Program p = new Program();
            p.RunThread();

        }
        public void RunThread()
        {
            for (int i = 0; i < threadPollMaxNUM; i++)
            {
                thread3 = new Thread(new ThreadStart(testFunc_three));
                thread3.Name = "thread" + i;
                thread3.Start();
            }
            string re = Console.ReadLine();
            if (re == "exit")
            {
                running = false;
            }
        }

        private void TestFunc(string str)
        {
            Console.WriteLine("{0} {1}", str, System.DateTime.Now.Millisecond.ToString());
            Thread.Sleep(50);
        }
        private void TestFunc_one(string str)
        {
            Console.WriteLine("sinco{0}{1}", str, System.DateTime.Now.Millisecond.ToString());
            Thread.Sleep(5000);
        }


        //以下是弹性处理任务的模型

        bool running = true;

        private void testFunc_three()
        {

            while (running)
            {

                mutex.WaitOne();
                //bool _havaTask = false;
                //lock (lockObject)
                //{
                    int ix = 0; //仅作为自动退出用,实际用时不需要

                    bool _havaTask = false;
                    while (_havaTask == false && running)
                    {
                        Console.WriteLine("{0} checking...", Thread.CurrentThread.Name);
                        _havaTask = getOneTask();
                        if (_havaTask == false)
                        {
                            //real sleep
                            Thread.Sleep(4000);

                            ix++;
                            if (ix > 5) { running = false; }//仅作为自动退出用,实际用时不需要
                        }
                    }
                //}
                //'' ""
                mutex.ReleaseMutex();

                if (_havaTask)
                {
                    Console.WriteLine("{0} working...", Thread.CurrentThread.Name);

                    //do some thing....
                    Thread.Sleep(5000);

                    Console.WriteLine("{0} end !", Thread.CurrentThread.Name);
                }

            }



            Console.WriteLine("{0} exit !", Thread.CurrentThread.Name);
        }

        int u = 0;
        /// <summary>
        /// 假设这是一个拉任务的方法
        /// </summary>
        /// <returns></returns>
        private bool getOneTask()
        {
            if (u < 6)
            {
                u++;
                Thread.Sleep(1000);
                return true;
            }
            else
            {
                //Thread.Sleep(30 * 1000);
                //running = false;
                return false;
            }
        }
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值