linux c线程池小结
2015-04-15 01:08 枫桥夜泊-霜满天 阅读(234) 评论(0) 收藏 举报使用线程池的场景是服务端线程执行时间很短,并且线程的创建和销毁非常频繁,这时候利用线程池可以很好的提升服务端线程,减少线程频繁创建和销毁的开销!
线程池的总体思路是:一个任务队列,若干已经创建好的线程,线程不停的检查任务队列是否有任务,有的话,取出执行,没有就等待,知道任务队列中有任务。
示例代码:
任务队列结构体:
typedef struct Job
{
void * (*function)(void *arg); //线程执行实际工作的函数指针
void* arg; //函数的参数
struct job *next //结构体自引用指针
}Work; //通过该结构体可以创建一个任务队列,用来存储任务
线程池结构体:
typedef struct Pool
{
int job_cur_num; //队列中目前的任务数
int pthread_max_num; //线程池中线程数目
int shutDown; //线程池关闭的标志
pthread_t * threadid;
pthread_mutex_t job_mutex; //线程互池量
pthread_cond_t job_cond; //线程条件变量
Work *jobs; //任务队列指针
}Thread_pool;
/******************** 申明函数和变量***********************************/
static Thread_pool* pool; //线程池指针
void* process(void*); //线程实际工作函数
void* thread_fun(void*); //线程执行函数
void pool_init(int); //线程池初始化函数
void pool_add_job(void*(*fun)(void*),void*); //向任务队列添加任务的函数
void free_pool();
void pool_init(int num)
{
int i;
pool = (Thread_pool*)malloc(sizeof(Thread_pool));
if(pool == NULL)
{
printf("init pool failed\n");
exit(1);
}
pool->job_cur_num = 0;
pool->thread_max_num = num;
pool->shutDown = 0;
pool->jobs = NULL;
pthread_mutex_init(&(pool->job_mutex),NULL);
pthread_mutex_init(&(pool->job_cond),NULL);
for(i=0;i<pool->thread_max_num;i++)
{
pthread_create(&(pool->threadid[i],NULL,thread_fun,NULL));
}
}
void pool_add_job(void* (*p)(void*arg),void* arg)
{
Work * w = NULL;
w = (Work*)malloc(sizeof(Work));
w->funtion = p;
w->arg = arg;
pthread_mutex_init(&(pool->job_mutex));//在这里要上锁,因为pool是全局变量,在其他线程里面也会使用,上锁保证每次操作的唯一性
Work * temp = pool->jobs;
if(temp!=NULL)
{
while(temp->next!=NULL)
{
temp = temp->next;
}
temp->next = w;
}
else
{
pool->jobs = w;
}
pthread_mutex_unlock(&(pool->job_mutex));
pthread_cond_signal(&(pool->job_cond));//通知等待的线程执行任务
}
void* thread_fun(void*arg)//从任务队列里面取出任务,并执行,如果没有,线程进入等待模式
{
while(1)
{
pthread_mutex_lock(&(pool->job_mutex));
while(pool->job_cur_num == 0 && !pool->shutDown)
{
pthread_cond_wait(&(pool->job_cond),&(pool->job_mutex));//如果任务队列没有任务,线程进入等待模式,直到被唤醒,等待后,互斥锁解锁,唤醒后,互斥锁加锁
}
Work * job = NULL;
job = pool->jobs;
pool->jobs = pool->jobs->next;
pthread_mutex_unlock(&(pool->job_mutex));
(*(job->function))(job->arg);
free(job);
}
}
void* process(void*arg)
{
printf("thread run at 0x%x,task is:%s",(char*)arg);
}
void free_pool()
{
int i;
pool->shutDown = 1;
//销毁线程池中的线程
pthread_cond_broadcast(&(pool->job_cond));//唤醒所有等待线程
for(i=0;i<pool->thread_max_num;i++)
{
pthread_join(pool->threadid[i],NULL);//等待所有线程执行结束
}
free(pool->threadid);//释放内存
//销毁任务队列呢内容
Work * temp = NULL;
temp = pool->jobs;
while(temp!=NULL)
{
free(temp);
temp = NULL;
pool->jobs = pool->jobs->next;
temp = pool->jobs;
}
//销毁互斥量和条件变量
pthread_mutex_destroy(&(pool->job_mutex));
pthread_cond_destroy(&(pool->job_cond));
free(pool);
pool = NULL;
}
int main(int argc,char*argv[])
{
int i;
pool_init(4);
pool_add_job(process,"run1");
pool_add_job(process,"run2");
pool_add_job(process,"run3");
pool_add_job(process,"run4");
pool_add_job(process,"run5");
pool_add_jobs(process,"run6");
pool_add_jobs(process,"run7");
pool_add_jobs(process,"run8");
pool_add_jobs(process,"run9");
pool_add_jobs(process,"run10");
sleep(5);//等待线程执行结束
free_pool();
}
return 0;
}
浙公网安备 33010602011771号