21xrx.com
2024-11-05 17:23:45 Tuesday
登录
文章检索 我的文章 写文章
C++ 手写线程池实现
2023-06-23 03:58:45 深夜i     --     --
C++ 手写 线程池 实现

    return !task_list.empty() || stop_task;

线程池是一种可以实现并发的方法,它可以最大程度地利用 CPU 资源,提高代码执行效率。C++ 程序员可以手写一个高效的线程池,以满足自己的需求,提升程序性能。

C++ 实现线程池,首先需要了解线程池的概念和工作原理。线程池是一种线程管理技术,它将一组线程预先创建并维护在一个队列中,可根据需要调度执行特定的任务。

实现线程池,需要首先创建线程池类,定义私有属性(线程数量、任务队列等),并且写出线程池的构造函数和析构函数。构造函数需要初始化线程池中的线程数量,如下所示:


ThreadPool::ThreadPool(int thread_num)

{

 this->thread_num = thread_num;

 this->stop_task = false;

 // 创建指定数量的线程

 for (int i = 0; i < thread_num; ++i)

 {

  thread_list.push_back(new std::thread(std::bind(&ThreadPool::thread_func, this)));

 }

}

以上代码中使用了 STL 的 vector 存储每个线程,并使用函数对象 std::bind 绑定函数和参数,让每个线程执行相同的线程函数。

在线程池中,需要实现任务队列,当线程池中没有任务时,线程阻塞并等待。如果有任务,则需要维护一个队列,将任务添加到队列中,在线程中不断取出任务并执行。实现线程池的核心函数如下:


void ThreadPool::thread_func() {

 while (true) {

  std::unique_lock<std::mutex> locker(task_mutex);

  task_cond.wait(locker, [this]() {

    return !task_list.empty() || stop_task;

  });

  if (stop_task)

   break;

  auto task = task_list.front();

  task_list.pop();

  locker.unlock();

  task();

 }

}

以上代码中使用了 std::unique_lock 来保证线程安全,使用 std::condition_variable 实现线程阻塞、互斥锁和条件变量等机制。

最后,我们需要实现向线程池中添加任务的方法:


template <typename F, typename... Args>

auto ThreadPool::enqueue(F&& f, Args&&... args)

  -> std::future<typename std::result_of<F(Args...)>::type> {

 using return_type = typename std::result_of<F(Args...)>::type;

 auto task = std::make_shared<std::packaged_task<return_type()>>(

   std::bind(std::forward<F>(f), std::forward<Args>(args)...));

 std::future<return_type> result = task->get_future();

 task_list.push([task]() { (*task)(); });

 task_cond.notify_one();

 return result;

}

以上代码中实现了任务的封装,使用了 std::packaged_task 来将函数对象封装为任务,使用 std::future 来获取任务执行结果,并将任务添加到任务队列中。

作为 C++ 程序员,可以使用线程池来提高程序性能。通过编写高效的代码,掌握 C++ 线程库的知识,手写线程池也是可以实现的。希望本文对你有所帮助。

  
  

评论区

{{item['qq_nickname']}}
()
回复
回复