# C++中的条件边量

# 介绍

std::condition_variable是和互斥量std::mutex一起使用的同步原语,用来阻塞一个或多个线程,直到有个线程修改了共享变量,并将其结果通知给std::condition_variable

修改共享变量的线程需做以下工作:

  • 获取互斥量std::mutex
  • 获取锁后修改共享变量
  • 调用notify_one或者notify_all

即便共享变量是原子量,也必须在获取到互斥量后才能正确的将修改通知给等待的线程。等待std::condition_variable的线程需要满足:

  • 获取std::unique_lock<std::mutex>以保护共享变量
  • 检查条件,以免已被更新
  • 使用wait, wait_forwait_until函数阻塞线程等待条件成立

# 代码实例

#include <iostream>
#include <thread>
#include <mutex>
#include <condition_variable>

std::mutex mtx;
std::condition_variable cond_var;
bool data_ready = false;

void producer() {
    while (true)
    {
        // Simulate some work...
        std::this_thread::sleep_for(std::chrono::seconds(2));
        // Modify shared data
        {
            std::lock_guard<std::mutex> lock(mtx);
            data_ready = true;
        }
        // Notify waiting threads
        cond_var.notify_one();
    }
}

void consumer() {
    // auto f1 = []()->bool { 
    //         std::cout << "consumer" << std::endl;
    //         return data_ready; };
    while (true)
    {        
        std::unique_lock<std::mutex> lock(mtx);
        cond_var.wait(lock);
        data_ready = false;
        // Continue processing after data is ready
        std::cout << "Consumer: Data is ready!" << std::endl;
    }
    
}

int main() {
    std::thread t1(producer);
    std::thread t2(consumer);

    t1.join();
    t2.join();

    return 0;
}

上面代码中的f1函数,可以传递给wait函数做第二个参数,用以校验等待条件是否成立。

# reference

1.https://en.cppreference.com/w/cpp/thread/condition_variable/wait (opens new window)