【C++基础知识】线程池、内存池、连接池的实现

//=============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 ThreadPool::add_task(void* (*run)(void *arg), void *arg) {
    pthread_mutex_lock(&mutex);  // 生成新的任务
    Task *task = new Task;
    task->run = run;
    task->arg = arg;
    tasks.push_back(task);  // 如果有等待线程,则唤醒一个
    if (idle > 0) {
        pthread_cond_signal(&cond);
    } else if (counter < threads) {
        pthread_t tid;
        pthread_create(&tid, NULL, ThreadPool::process, (void*)this);
        this->counter++;
    }
    pthread_mutex_unlock(&mutex);
}
 
void ThreadPool::threadpool_destroy() {
    if (shutdown) {
        return;
    }
    pthread_mutex_lock(&mutex);
    shutdown = true;
    if (counter > 0) {  // 唤醒空闲线程退出
        if (idle > 0) {
            pthread_cond_broadcast(&cond);
        }  // 如果线程处于执行阶段,等待任务执行完毕之后退出
        while (counter > 0) {
            pthread_cond_wait(&cond, &mutex);
        }
    }
    pthread_mutex_unlock(&mutex);
    pthread_mutex_destroy(&mutex);
}

//=============threadpool.h==========

#ifndef _THREADPOOL_H
#define _THREADPOOL_H
 
#include <vector>
#include <pthread.h>
#include <time.h>
#include <errno.h>
#include <iostream>
 
struct 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;
}

猜你喜欢

转载自www.cnblogs.com/wangzming/p/11564578.html
今日推荐