线程池实现

来源:互联网 发布:审核员 知乎 编辑:程序博客网 时间:2024/06/06 11:01

  什么时候需要创建线程池呢?简单的说,如果一个应用需要频繁的创建和销毁线程,而任务执行的时间又非常短,这样线程创建和销毁的带来的开销就不容忽视,这时也是线程池该出场的机会了。如果线程创建和销毁时间相比任务执行时间可以忽略不计,则没有必要使用线程池了。

下面列出线程的一些重要的函数

  1. int pthread_create(pthread_t *threadconst pthread_attr_t *attr,  
  2.                    void *(*start_routine) (void *), void *arg);  
  3. void pthread_exit(void *retval);  
  4.   
  5. int pthread_mutex_destroy(pthread_mutex_t *mutex);  
  6. int pthread_mutex_init(pthread_mutex_t *restrict mutex,  
  7.                        const pthread_mutexattr_t *restrict attr);  
  8. int pthread_mutex_lock(pthread_mutex_t *mutex);  
  9. int pthread_mutex_trylock(pthread_mutex_t *mutex);  
  10. int pthread_mutex_unlock(pthread_mutex_t *mutex);  
  11.   
  12. int pthread_cond_destroy(pthread_cond_t *cond);  
  13. int pthread_cond_init(pthread_cond_t *restrict cond,  
  14.                       const pthread_condattr_t *restrict attr);  
  15. int pthread_cond_destroy(pthread_cond_t *cond);  
  16. int pthread_cond_init(pthread_cond_t *restrict cond,  
  17.                       const pthread_condattr_t *restrict attr);  
  18. int pthread_cond_broadcast(pthread_cond_t *cond);  
  19. int pthread_cond_signal(pthread_cond_t *cond);  

下面是用C++实现线程池源码:
在该源码中,有两个文件,一个头文件pmutil.h, 一个源文件pmulti.cpp文件
下面是 pmuti.h 文件

  1. #include <pthread.h>  
  2.       typedef struct  worker_node{ /*任务结点*/  
  3.           void *(*process)(void *arg);  
  4.           void *arg;  
  5.           worker_node *next;  
  6.   }worker_node;  
  7.   typedef struct worker_queue{/*任务队列*/  
  8.   private:  
  9.       worker_node * head ,*tail ;  
  10.       int cur_size ;  
  11.       pthread_cond_t ready ;/**保持同步*/  
  12.       pthread_mutex_t mutex ; /**保持互斥信号*/  
  13.       bool destroy ;  
  14.   public:  
  15.       worker_queue();   
  16.       ~worker_queue();  
  17.       int clean();   /*清空队列*/  
  18.       int in_queue(const worker_node *node);  /*任务入队*/  
  19.       worker_node * out_queue(); /*任务出队*/  
  20.   
  21.   } worker_queue ;  
  22.   
  23.   
  24.   class pmulti{  
  25.   private:  
  26.       pthread_t * threads ;  
  27.       unsigned int thread_num;  
  28.       mutable worker_queue * w_queue;  
  29.       bool is_init;  
  30.       bool is_destroy;  
  31.       enum {QUEUE_MAX_SIZE=100};  
  32.   public:  
  33.       pmulti();  
  34.       ~pmulti();  
  35.       int init(unsigned int num=10);  
  36.       static void * thread_fun(void *arg); /*线程执行主函数*/  
  37.       int add_worker(const worker_node * node); /*增加任务*/  
  38.   
  39.       int destroy();  
  40.   };  

  pmulti.cpp文件

  1. #include <stdio.h>  
  2. #include <unistd.h>  
  3. #include <string.h>  
  4. #include <assert.h>  
  5. #include "multi.h"  
  6. worker_queue::worker_queue():head(NULL),tail(NULL),cur_size(0),destroy(false){  
  7.     pthread_mutex_init(&mutex,NULL);  
  8.     pthread_cond_init(&ready,NULL);  
  9. }  
  10. worker_queue::~worker_queue(){  
  11.     clean();  
  12.     destroy = true ;  
  13.     pthread_cond_broadcast(&ready);  
  14.     pthread_mutex_destroy(&mutex);   
  15.     pthread_cond_destroy(&ready);  
  16. }     
  17. int worker_queue::clean(){   
  18.     worker_node* temp;  
  19.     pthread_mutex_lock(&mutex);  
  20.     while(NULL!=head){  
  21.         temp = head ;  
  22.         head = head->next ;   
  23.         delete temp ;  
  24.     }  
  25.     tail=head=NULL;  
  26.     cur_size = 0;  
  27.     pthread_mutex_unlock(&mutex);  
  28.     return 0;  
  29. }  
  30. int worker_queue::in_queue(const worker_node *node){  
  31.     worker_node *temp;  
  32.     temp = new worker_node ;  
  33.     if(NULL == temp) return -1 ; //new err ;  
  34.     *temp = *node ;  
  35.     pthread_mutex_lock(&mutex);  
  36.   
  37.     if(NULL==head){  
  38.         head=tail=temp;  
  39.     }else{  
  40.         tail->next=temp ;  
  41.         tail = temp ;  
  42.         tail->next = NULL;  
  43.     }  
  44.     cur_size++;  
  45.     pthread_mutex_unlock(&mutex);  
  46.     pthread_cond_signal(&ready);  
  47.     return 0 ;  
  48. }  
  49. worker_node * worker_queue::out_queue(){ //out of the queue  
  50.     pthread_mutex_lock(&mutex);  
  51.     if((NULL==head) && (false == destroy))  { //queue empty  
  52.         pthread_cond_wait(&ready,&mutex);  
  53.     }  
  54.     //      assert(head!=NULL);  
  55.     //      assert(cur_size!=0);  
  56.     if(destroy){  
  57.         pthread_mutex_unlock(&mutex);  
  58.         return NULL;  
  59.     }  
  60.     worker_node *temp;  
  61.     temp = head ;  
  62.     head = head->next ;  
  63.     cur_size -- ;  
  64.   
  65.   
  66.     pthread_mutex_unlock(&mutex);  
  67.     return temp;  
  68. }  
  69. pmulti::pmulti():  
  70. is_init(false),thread_num(0),w_queue(NULL),threads(NULL),is_destroy(false){  
  71. }  
  72. pmulti::~pmulti(){  
  73. }  
  74. int pmulti::init(unsigned int thr_num){  
  75.     if(is_init)  
  76.         return -1;//alread init   
  77.     int i;  
  78.     //pool = new thread_pool;  
  79.     //if(NULL == pool)      return -2;//new error  
  80.     //bzero(pool,sizeof(thread_pool));  
  81.     w_queue = new worker_queue ;  
  82.     if(NULL == w_queue)     return -2;//new error  
  83.     thread_num = thr_num;  
  84.     threads = new pthread_t[thr_num] ;  
  85.     for(i=0;i<thr_num;i++){  
  86.         if(0!=pthread_create((threads+i),NULL,thread_fun,(void*)this ))  
  87.             printf("pthread_create error\n");  
  88.     }   
  89.     is_destroy = false ;  
  90.     is_init = true;  
  91.     return 0;  
  92. }  
  93. int pmulti::add_worker(const worker_node * node){  
  94.     return  w_queue->in_queue(node);  
  95. }  
  96. int pmulti::destroy(){  
  97.     int i=0;  
  98.     char* res;  
  99.     is_destroy = true ;  
  100.     if(NULL != w_queue)              
  101.         delete w_queue;          
  102.     for(i=0;i<thread_num;i++){                 
  103.         pthread_join(threads[i],(void**)&res);                  
  104.         printf("joined :%lld  end;\n",res);          
  105.     }          
  106.     if(thread_num > 0)    
  107.         delete[] threads;          
  108.     return 0;  
  109. }  
  110. void* pmulti::thread_fun(void*arg){          
  111.     printf("thread num:%lld\n",pthread_self());          
  112.     pmulti *pm =(pmulti*)arg;          
  113.     worker_node * node ;          
  114.     while(1){                 
  115.         if(pm->is_destroy)                          
  116.             pthread_exit(NULL);                  
  117.         node = pm->w_queue->out_queue();                  
  118.         if((NULL == node)|| (pm->is_destroy))                          
  119.             pthread_exit(NULL);                  
  120.         node->process(node->arg);                  
  121.         printf("thread_fun:%lld run\n",pthread_self());          
  122.     }          
  123.     return (void*)pthread_self();  
  124. }  

  1. void * test(void* i){          
  2.     printf("test:%d\n",( int)i);          
  3.     sleep(1);          
  4.     return NULL;  
  5. }  
  6. int main(int argc,char ** args){          
  7.     printf("this is main!\n");          
  8.     class pmulti pm;          
  9.     pm.init(15);          
  10.     worker_node no ;          
  11.     for(int i=0;i<5;i++){                  
  12.         no.process = &test ;                  
  13.         no.arg = (void*)(i*2);                  
  14.         pm.add_worker(&no);          
  15.     }          
  16.     sleep(5);          
  17.     pm.destroy();         
  18.     return 0;  
  19. }  
运行结果:
g++ multi.cpp multi.h -lpthread -o multi
[test@localhost multi_thread]$ ./multi 
this is main!
thread num:24531909488
test:0
thread num:3046583152
test:2
thread num:3036093296
test:4
thread num:3025603440
test:6
thread num:3015113584
test:8
thread num:3004623728
thread num:3067562864
thread num:2994133872
thread num:2983644016
thread num:2973154160
thread num:2962664304
thread num:2952174448
thread num:2941684592
thread num:2931194736
thread num:3078052720
thread_fun:24531909488 run
thread_fun:3046583152 run
thread_fun:3036093296 run
thread_fun:3025603440 run
thread_fun:3015113584 run
joined :0  end;
joined :0  end;
joined :0  end;
joined :0  end;
joined :0  end;
joined :0  end;
joined :0  end;
joined :0  end;
joined :0  end;
joined :0  end;
joined :0  end;
joined :0  end;
joined :0  end;
joined :0  end;


参考博客:http://hi.baidu.com/boahegcrmdghots/item/f3ca1a3c2d47fcc52e8ec2e1

转自csdn博客:

http://blog.csdn.net/rao_warrior/article/details/8607228
原创粉丝点击