条件变量的作用(条件变量原理)

条件变量的作用(条件变量原理)condition variable 类是一个同步原语 与 std mutex 一起使用 用于阻塞一个或多个线程 直到另一个线程修改一个共享变量 条件 并通知 condition variable condition variable 主要有 wait 函数和 notify 函数 wait 的作用是等待 notify 的作用是通知 Linux 环境下的相关接口 pthread cond 等函数 当 std

大家好,我是讯享网,很高兴认识大家。



condition_variable类是一个同步原语,与std::mutex一起使用,用于阻塞一个或多个线程,直到另一个线程修改一个共享变量(条件)并通知condition_variable。condition_variable主要有wait函数和notify_* 函数,wait的作用是等待,notify的作用是通知。Linux环境下的相关接口pthread_cond_*等函数。

当 std::condition_variable对象的某个wait 函数被调用的时候,它使用 std::unique_lock(通过 std::mutex) 来锁住当前线程。当前线程会一直被阻塞,直到另外一个线程在相同的 std::condition_variable 对象上调用了 notification 函数来唤醒当前线程。

wait()还有第二个参数,这个参数接收一个布尔类型的值,当这个布尔类型的值为false的时候线程就会被阻塞在这里,只有当线程被唤醒之后,且第二参数为true才会往下运行。

notify_one()每次只能唤醒一个线程,notify_all()函数的作用就是可以唤醒所有的线程,但是最终能抢夺锁的只有一个线程,或者说有多个线程在wait,但是用notify_one()去唤醒其中一个线程,那么这些线程就出现了去争夺互斥量的情况,最终没有获得锁的控制权的线程就会再次回到阻塞的状态,对于这些没有抢到控制权的过程叫做虚假唤醒。对于虚假唤醒的解决方法就是加一个while()循环,比如:

 

讯享网

这个就是当线程被唤醒以后,先进行判断,是否可以去操作,如果可以,再去运行下面的代码,否则继续在循环内执行wait函数

上面所说多个线程等待一个唤醒的情况叫做惊群效应。

方法原型:


讯享网

讯享网

std::condition_variable提供了两种wait()函数。当前线程调用wait()后被阻塞(此时当前线程获得了mutex),直到另外某个线程调用notify_*唤醒了当前线程。

在当前线程被阻塞时,该函数会自动调用lck.unlock()释放锁,使得其他被阻塞在锁竞争上的线程得以继续执行。一旦当前线程获得通知(通常是另外某个线程调用notify_* 唤醒了当前线程),wait()函数也是自动调用lck.lock(),使得lck的状态和wait函数被调用时相同。

在设置了pred的情况下,只有当pred条件为false时调用wait()才会阻塞当前线程,并且在收到其他线程的通知后只有当pred为true时才会被解除阻塞。等效于以下情景。

 

方法原型:

讯享网

与std::condition_variable::wait()类似,不过wait_for可以指定一个时间段,在当前线程收到通知或者指定的时间rel_time超时之前,该线程都会处于阻塞状态。一旦超时或收到了其他线程的通知,wait_for返回,剩下的处理步骤和wait()类似。

wait_for()的pred表示预测条件,只有当pred条件为false时调用wait()才会阻塞当前线程,并且在收到其他线程的通知后只有当pred为true时才会被解除阻塞。

方法原型:

 

与wait_for类似,但是wait_until可以指定一个时间点,在当前线程收到通知或者指定的时间点abs_time超时之前,该线程都处于阻塞状态。一旦超时或者收到了其他线程的通知,wait_until返回,剩下的处理步骤和wait()相似

wait_until的重载版本中pred表示wait_until的预测条件,只有当pred条件为false时调用wait()才会阻塞当前线程,并且在收到其他线程的通知后只有当pred为true时才会被解除阻塞

唤醒某个等待(wait)线程。如果当前没有等待线程,则该函数什么也不做,如果同时存在多个等待线程,则唤醒某个线程是不确定的。

唤醒所有等待(wait)线程。如果当前没有等待线程,则什么也不做。

通知其他线程,给定的线程已经全部完成,当调用该函数的线程退出时,所有在cond条件变量上等待的线程都会收到通知

与std::condition_variable类似,只不过std::condition_variable_any的wait函数可以接受任何lockadle参数。而std::condition_variable只能接受std::unique_lock类型的参数,除此意外和std::condition_variable几乎完全一样。

讯享网

运行结果:

 










参考文章:

https://cloud.tencent.com/developer/article/
https://en.cppreference.com/w/cpp/thread/condition_variable
https://blog.csdn.net/lv0918_qian/article/details/

小讯
上一篇 2025-06-09 10:18
下一篇 2025-06-01 14:42

相关推荐

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容,请联系我们,一经查实,本站将立刻删除。
如需转载请保留出处:https://51itzy.com/kjqy/163828.html