21xrx.com
2024-11-22 06:22:46 Friday
登录
文章检索 我的文章 写文章
使用c++11的线程池实现子任务分配和处理
2023-06-28 18:00:24 深夜i     --     --
C++11 线程池 子任务 分配 处理
return this->stop || !this->tasks.empty();

在日常的编程中,我们经常需要处理大量的数据或者进行复杂的操作。这时候,如果我们使用单一的线程进行处理,往往效率会非常低下,尤其是当数据量非常大的时候。因此,我们需要使用线程池来进行任务的分配和处理。

线程池是由多个线程组成的,可以使得我们的程序可以同时处理多个任务。其中,线程池会维护一个任务队列,当有任务需要处理时,会从队列中取出一个任务交给空闲的线程去处理。这样可以使得我们的程序可以非常快速地处理大量的任务,提高了我们程序的效率。

在C++11中,提供了一套非常方便的线程池库,可以帮助我们快速地实现线程池。下面,我们来看一下具体的例子。


#include <iostream>

#include <thread>

#include <vector>

#include <queue>

#include <mutex>

#include <condition_variable>

class ThreadPool {

public:

  ThreadPool(size_t threads) : stop(false) {

    for (size_t i = 0; i < threads; ++i)

      workers.emplace_back([this] {

        for (;;) {

          std::function<void()> task;

          {

            std::unique_lock<std::mutex> lock(this->queue_mutex);

            this->condition.wait(lock, [this] { return this->stop || !this->tasks.empty(); });

            if (this->stop && this->tasks.empty())

             return;

            task = std::move(this->tasks.front());

            this->tasks.pop();

          }

          task();

        }

      });

  }

  template <class F>

  void enqueue(F&& f) {

    {

      std::unique_lock<std::mutex> lock(queue_mutex);

      tasks.emplace([f] {

        f();

      });

    }

    condition.notify_one();

  }

  ~ThreadPool() {

    {

      std::unique_lock<std::mutex> lock(queue_mutex);

      stop = true;

    }

    condition.notify_all();

    for (std::thread& worker : workers)

      worker.join();

  }

private:

  std::vector<std::thread> workers;

  std::queue<std::function<void()>> tasks;

  std::mutex queue_mutex;

  std::condition_variable condition;

  bool stop;

};

void subtask1() {

  std::cout << "Subtask 1 is being processed.\n";

}

void subtask2() {

  std::cout << "Subtask 2 is being processed.\n";

}

void subtask3() {

  std::cout << "Subtask 3 is being processed.\n";

}

int main()

{

  ThreadPool pool(4);

  // Add subtasks to the queue

  for (int i = 0; i < 10; i++) {

    pool.enqueue(subtask1);

    pool.enqueue(subtask2);

    pool.enqueue(subtask3);

  }

  // Wait for all tasks to be completed

  std::this_thread::sleep_for(std::chrono::seconds(1));

  return 0;

}

在这个例子中,我们首先定义了一个ThreadPool类。在它的构造函数中,我们通过std::thread来创建指定数量的线程。然后,我们定义了一个enqueue()方法,这个方法可以将一个函数放到任务队列中,准备被线程池中的某个线程处理。在enqueue()方法中,我们首先通过std::unique_lock 来上锁,然后将需要执行的函数放到任务队列中,并触发condition变量,告诉线程池中的线程有新的任务需要处理。在ThreadPool类的析构函数中,我们会等待所有线程完成自己所分配的任务,然后再关闭线程。

下面是一个示例,展示了如何将一些子任务加入到任务队列中,并且等待所有任务完成:


ThreadPool pool(4);

// Add subtasks to the queue

for (int i = 0; i < 10; i++) {

  pool.enqueue(subtask1);

  pool.enqueue(subtask2);

  pool.enqueue(subtask3);

}

// Wait for all tasks to be completed

std::this_thread::sleep_for(std::chrono::seconds(1));

通过线程池,我们可以将一些原本需要顺序执行的子任务分配给多个线程,让多个线程同时处理任务,从而提高程序的效率。总的来说,使用C++11的线程池来实现子任务分配和处理非常方便,而且能够有效地提高程序的性能。

  
  

评论区

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