//=============threadpool.c========== #include "threadpool.h" #include <stdio.h> pthread_mutex_t ThreadPool::mutex = PTHREAD_MUTEX_INITIALIZER; pthread_cond_t ThreadPool::cond = PTHREAD_COND_INITIALIZER; std::vector<Task*> ThreadPool::tasks; ThreadPool::ThreadPool(int threads) { this->threads = threads; this->shutdown = false; this->counter = 0; this->idle = 0; } void* ThreadPool::process(void *arg) { struct timespec abstime; int timeout; ThreadPool *pool = static_cast<ThreadPool*>(arg); printf("thread 0x%0x is starting\n", (int)pthread_self()); while (true) { pthread_mutex_lock(&mutex); pool->idle++; timeout = 0; while (tasks.empty() && !pool->shutdown) { clock_gettime(CLOCK_REALTIME, &abstime); abstime.tv_sec += 2; int status = pthread_cond_timedwait(&cond, &mutex, &abstime); if (status == ETIMEDOUT) { printf("thread 0x%0x is waiting time out\n", (int)pthread_self()); timeout = -1; break; } } pool->idle--; if (!tasks.empty()) { Task *task = tasks.back(); tasks.pop_back(); // 执行任务 pthread_mutex_unlock(&mutex); task->run(task->arg); delete task; pthread_mutex_lock(&mutex); } if (pool->shutdown && tasks.empty()) { pool->counter--; if (pool->counter == 0) { pthread_cond_signal(&cond); } pthread_mutex_unlock(&mutex); break; } if (timeout == -1 && tasks.empty()) { // if it is timeout,the thread will end(why not keep it? because it means no more works are added now) pool->counter--; pthread_mutex_unlock(&mutex); break; } pthread_mutex_unlock(&mutex); } printf("thread 0x%0x is exiting\n", (int)pthread_self()); return NULL; } void:: add_task the ThreadPool ( void* (* RUN) ( void * Arg), void * Arg) { the pthread_mutex_lock ( & the mutex); // create a new task of the Task Task * = new new the Task; Task -> = RUN RUN; Task -> Arg = Arg; tasks.push_back (Task); // if waiting threads, a wake- IF (IDLE> 0 ) { a pthread_cond_signal ( & cond); } the else IF (counter < threads) { pthread_t TID; pthread_create ( & TID, NULL, the ThreadPool :: Process , ( void*) The this ); the this -> counter ++ ; } pthread_mutex_unlock ( & the mutex); } void the ThreadPool :: threadpool_destroy () { IF (the shutdown) { return ; } the pthread_mutex_lock ( & the mutex); the shutdown = to true ; IF (counter> 0 ) { // wake idle thread exits IF (iDLE> 0 ) { pthread_cond_broadcast ( & cond); } // exit if the thread is in the implementation phase after waiting task is finished the while (counter> 0 ) { pthread_cond_wait ( & cond, & mutex); } } pthread_mutex_unlock ( & mutex); pthread_mutex_destroy ( & mutex); } // === the ThreadPool.h ========== ========== #ifndef _THREADPOOL_H #define _THREADPOOL_H #include <Vector> #include <pthread.h> #include <time.h> #include <errno.h> #include <the iostream> struct the Task { void* (*run)(void *arg); void *arg; }; class ThreadPool { private: int threads; static std::vector<Task*> tasks; static pthread_mutex_t mutex; static pthread_cond_t cond; static void *process(void *arg); bool shutdown; int counter; int idle; public: ThreadPool(int threads_); ~ThreadPool() {}; void add_task(void* (*task)(void *arg), void *arg); void threadpool_destroy(); }; #endif /*_THREADPOOL_H*/ //=============main.c========== #include "threadpool.h" #include <iostream> #include <vector> #include <stdio.h> #include <unistd.h> void* func1(void* arg) { int cnt = 0; while (1) { int tid = pthread_self(); printf("[func1]0x%0x thread, cnt = %d\n", tid, cnt); cnt += 1; sleep(2); } } void* func2(void* arg) { int cnt = 1; while (1) { int tid = pthread_self(); printf("[func2]0x%0x thread, cnt = %d\n", tid, cnt); cnt *= 3; sleep(3); } } int main() { ThreadPool pool(3); //Task task = {func1, NULL}; for (int i = 0; i < 10; i++) { pool.add_task(&func1, NULL); } pool.add_task(&func2, NULL); while (1) { } return 0; }