21xrx.com
2025-04-17 00:20:34 Thursday
文章检索 我的文章 写文章
C++11中的信号量实现
2023-06-29 05:37:17 深夜i     31     0
C++11 信号量 实现

信号量是一种用于协调多个线程之间共享资源的机制。在C++11中,标准库中提供了一个std::semaphore类用于实现信号量。这篇文章将介绍在C++11中实现信号量的方法以及如何使用std::semaphore类来实现。

实现信号量的方法

在C++11中,我们可以使用互斥锁和条件变量来实现信号量。一个信号量包含两个基本操作,P(等待信号量)和V(释放信号量)。我们可以使用互斥锁来同步多个线程对信号量的访问,并使用条件变量来等待和通知线程。

使用std::semaphore类实现信号量

std::semaphore类是C++11中标准库提供的实现信号量的类。它包含两个基本操作,wait()和signal(),对应P和V操作。每当一个线程调用wait()方法时,如果信号量的值大于0,信号量的值减1,并立即返回;否则线程会被阻塞。当另一个线程调用signal()方法时,信号量的值增加1,并通知等待在信号量上的线程可以继续执行。

以下是使用std::semaphore类实现生产者-消费者问题的示例代码:

#include <iostream>
#include <thread>
#include <mutex>
#include <condition_variable>
#include <chrono>
#include <semaphore>
std::mutex mtx;
std::queue<int> q;
std::condition_variable cv;
std::semaphore sem(1);
void producer()
{
  for (int i = 0; i < 10; ++i)
  {
    std::this_thread::sleep_for(std::chrono::milliseconds(500)); // 模拟生产数据的操作
    sem.wait(); // 等待信号量
    std::unique_lock<std::mutex> lck(mtx);
    q.push(i); // 生产数据
    std::cout << "Produced " << i << std::endl;
    sem.signal(); // 释放信号量
    cv.notify_one(); // 通知一个等待的线程
  }
}
void consumer()
{
  for (int i = 0; i < 10; ++i)
  {
    std::unique_lock<std::mutex> lck(mtx);
    cv.wait(lck, [] { return !q.empty(); }); // 等待非空队列
    sem.wait(); // 等待信号量
    int data = q.front(); // 消费数据
    q.pop();
    std::cout << "Consumed " << data << std::endl;
    sem.signal(); // 释放信号量
  }
}
int main()
{
  std::thread t_producer(producer);
  std::thread t_consumer(consumer);
  t_producer.join();
  t_consumer.join();
  return 0;
}

总结

信号量是一种用于协调多个线程之间共享资源的机制,C++11中提供了std::semaphore类来实现信号量。使用互斥锁和条件变量可以实现信号量,但使用std::semaphore类更加简单方便。在使用信号量时,需要注意同步多个线程对信号量的访问,以及等待和通知线程的正确使用。

  
  

评论区