C++实现一个简单的线程池
工作中需要用到多线程,就简单实现了一个简易的线程池,直接上代码记录一下
#ifndef THREADPOOL_H
#define THREADPOOL_H
#include <thread>
#include <mutex>
#include <condition_variable>
#include <vector>
#include <functional>
#include <queue>
class ThreadPool
{
public:
//自定义void()的函数类型
typedef std::function<void()> Task;
/*! \brief 构建一个具有threadCount个线程的线程池
* 如果线程数量为-1,则按当前CPU数给一个默认的线程数值
* \param[in] threadCount 线程数
*/
ThreadPool(int threadCount = -1);
~ThreadPool();
/*! \brief 开启线程池
* 启动当前创建的线程池
* 线程进入等待状态
*/
void start();
/*! \brief 关闭线程池
* 关闭当前创建的线程池
* 如果没有任务了,则直接退出所有线程
* 如果还有任务没完成,等待全部完成后,退出所有线程
* 此方法会阻塞消息循环,直至所有线程退出
*/
void stop();
/*! \brief 添加一个任务
* 此方法会唤醒等待的线程进行任务的执行
* 如果没有启动线程池,此方法无效
*/
void addTask(const Task& ta);
private:
void runTask();
Task takeTask();
private:
std::vector<std::thread> threads;
std::queue<Task> taskqueue;//任务队列
std::condition_variable cond;
std::mutex m_mutex;
unsigned int m_threadCount;
bool over;
};
#endif // THREADPOOL_H
cpp
#include "threadpool.h"
ThreadPool::ThreadPool(int threadCount)
{
over = false;
m_threadCount = threadCount == -1 ? std::thread::hardware_concurrency() : threadCount;
}
ThreadPool::~ThreadPool()
{
}
void ThreadPool::start()
{
for (int i = 0; i < m_threadCount; ++i)
{
threads.push_back(std::thread(&ThreadPool::runTask, this));
}
}
void ThreadPool::addTask(const Task& ta)
{
if (threads.size() == 0)
{
return;
}
std::unique_lock<std::mutex> lck(m_mutex);
taskqueue.push(ta);
cond.notify_one();
}
void ThreadPool::stop()
{
{
std::unique_lock<std::mutex> lck(m_mutex);
over = true;
cond.notify_all();
}
for (int i = 0; i < m_threadCount; ++i)
{
threads[i].join();
}
threads.clear();
}
//跑任务的流程,如果有任务,就启动一个线程去跑,跑完了后检测有没有任务 有任务继续跑,没任务就等待
void ThreadPool::runTask()
{
//进入循环条件,线程池还未关闭 或者 任务还没执行完
while (!over || !taskqueue.empty())
{
Task ta = takeTask();
if (ta)
{
ta();
}
}
}
ThreadPool::Task ThreadPool::takeTask()
{
std::unique_lock<std::mutex> lck(m_mutex);
while (taskqueue.empty() && !over)
{//等待条件,任务为空 并且 线程池还未关闭
cond.wait(lck);
}
Task ta;
if (!taskqueue.empty())
{
ta = taskqueue.front();
taskqueue.pop();
}
return ta;
}
上述实现,可以创建一个固定线程数的线程池,并且当所有任务完成后才会退出。
参考1:https://blog.csdn.net/qq_41681241/article/details/86723964
参考2:https://www.cnblogs.com/ailumiyana/p/10016965.html