Version: 1.0
pool.h
Go to the documentation of this file.
1 // Extrapolated from https://vorbrodt.blog/2019/02/12/simple-thread-pool/
2 #pragma once
3 
4 #include <vector>
5 #include <thread>
6 #include <memory>
7 #include <future>
8 #include <functional>
9 #include <type_traits>
10 #include <cassert>
11 #include "queue.h"
12 
14 {
15 public:
17  unsigned int queueDepth = std::thread::hardware_concurrency(),
18  size_t threads = std::thread::hardware_concurrency())
19  : m_workQueue(queueDepth)
20  {
21  assert(queueDepth != 0);
22  assert(threads != 0);
23  for (size_t i = 0; i < threads; ++i)
24  m_threads.emplace_back(std::thread([this]() {
25  while (true)
26  {
27  auto workItem = m_workQueue.pop();
28  if (workItem == nullptr)
29  {
30  m_workQueue.push(nullptr);
31  break;
32  }
33  workItem();
34  }
35  }));
36  }
37 
38  ~thread_pool() noexcept
39  {
40  m_workQueue.push(nullptr);
41  for (auto& thread : m_threads)
42  thread.join();
43  }
44 
45  using Proc = std::function<void(void)>;
46 
47  template<typename F, typename... Args>
48  void enqueue_work(F&& f, Args&&... args) //noexcept(std::is_nothrow_invocable<decltype(&blocking_queue<Proc>::push<Proc&&>)>::value)
49  {
50  m_workQueue.push([=]() { std::invoke(f, args...); });
51  }
52 
53  template<typename F, typename... Args>
54  auto enqueue_task(F&& f, Args&&... args) -> std::future<typename std::result_of<F(Args...)>::type>
55  {
56  using return_type = typename std::result_of<F(Args...)>::type;
57  auto task = std::make_shared<std::packaged_task<return_type()>>(std::bind(std::forward<F>(f), std::forward<Args>(args)...));
58  std::future<return_type> res = task->get_future();
59  m_workQueue.push([task]() { (*task)(); });
60  return res;
61  }
62 
63 private:
64  using ThreadPool = std::vector<std::thread>;
65  ThreadPool m_threads;
66  blocking_queue<Proc> m_workQueue;
67 };
std::function< void(void)> Proc
Definition: pool.h:45
auto enqueue_task(F &&f, Args &&... args) -> std::future< typename std::result_of< F(Args...)>::type >
Definition: pool.h:54
void enqueue_work(F &&f, Args &&... args)
Definition: pool.h:48
thread_pool(unsigned int queueDepth=std::thread::hardware_concurrency(), size_t threads=std::thread::hardware_concurrency())
Definition: pool.h:16
~thread_pool() noexcept
Definition: pool.h:38