c语言编程笔录

首页 >   > 笔记大全

笔记大全

C++怎么实现简单的生产者-消费者队列

更新时间:2023-12-02

前言:

生产者-消费者问题是并发编程中经典的问题之一。在多线程环境下,生产者线程生成商品放入队列,消费者线程从队列中取出商品消费。这种场景常见于各种异步处理、任务调度等系统中,实现生产者-消费者队列即可用于解耦生产者和消费者,提高系统吞吐量。

生产者-消费者队列的实现:

下面是使用C++实现简单生产者-消费者队列的思路:

  1. 定义一个固定大小的队列作为生产者-消费者队列的缓冲区。
  2. 定义一个互斥锁来保护缓冲区的访问,防止多个线程同时访问共享资源。
  3. 定义一个条件变量,当缓冲区为空时,消费者线程等待;当缓冲区满时,生产者线程等待。
  4. 在生产者线程中,首先获取互斥锁,判断缓冲区是否已满,如果已满则等待条件变量;否则将商品放入缓冲区,通知条件变量有商品可取。
  5. 在消费者线程中,首先获取互斥锁,判断缓冲区是否为空,如果为空则等待条件变量;否则从缓冲区取出商品,通知条件变量有空位可放。
#include 
#include 
#include 
#include 
#include 

const int MAX_BUFFER_SIZE = 10;
std::queue buffer;
std::mutex mtx;
std::condition_variable cv;

void producer() {
  for (int i = 0; i < 100; ++i) {
    std::this_thread::sleep_for(std::chrono::milliseconds(100));
    std::unique_lock lock(mtx);
    cv.wait(lock, [] { return buffer.size() < MAX_BUFFER_SIZE; });
    buffer.push(i);
    std::cout << "Produced: " << i << std::endl;
    cv.notify_all();
  }
}

void consumer() {
  for (int i = 0; i < 100; ++i) {
    std::this_thread::sleep_for(std::chrono::milliseconds(200));
    std::unique_lock lock(mtx);
    cv.wait(lock, [] { return !buffer.empty(); });
    int item = buffer.front();
    buffer.pop();
    std::cout << "Consumed: " << item << std::endl;
    cv.notify_all();
  }
}

int main() {
  std::thread producerThread(producer);
  std::thread consumerThread(consumer);
  
  producerThread.join();
  consumerThread.join();
  
  return 0;
}

总结:

以上代码是一个简单的生产者-消费者队列的实现。通过使用互斥锁和条件变量,保证了线程之间的同步和互斥。生产者线程在缓冲区不满时将商品放入队列,并通知消费者线程有商品可取;消费者线程在缓冲区不为空时从队列中取出商品,并通知生产者线程有空位可放。这样,生产者和消费者线程之间可以并发执行,实现了生产者-消费者模型的基本功能。

需要注意的是,在实际应用中生产者-消费者队列还可能涉及更复杂的情况,如使用多个生产者和消费者线程、处理异常等。此外,上述代码中的缓冲区是一个简单的队列,可以根据实际需求进行定制,例如使用循环队列等数据结构。