如何在一个睡眠状态的std::thread中唤醒它?
介绍
在C++ 11标准中,std::thread是用于启动一个线程的重要类,它可以帮助我们轻松地实现多线程程序。然而,在某些情况下,我们可能需要让线程在特定的时间点进行休眠,并在特定时间点唤醒它。本文将介绍如何在一个睡眠状态的std::thread中唤醒它。
睡眠状态的std::thread
在std::thread中,有一个sleep_for的函数可以用来让线程休眠,如下所示的示例代码:
#include <iostream>
#include <chrono>
#include <thread>
void foo(int x){
std::cout << "start" << std::endl;
std::this_thread::sleep_for(std::chrono::seconds(x));
std::cout << "end" << std::endl;
}
int main(){
std::thread th(foo, 3);
th.join();
return 0;
}
在上面的代码中,我们定义了一个foo函数,它将在第一个输出start之后休眠3秒,然后输出end。main函数中启动了线程th,将参数3传递给foo函数,并等待线程执行完毕后结束程序。
唤醒睡眠状态的std::thread
如果我们在程序执行过程中想要唤醒一个处于睡眠状态的线程,该怎么做呢?在C++中,提供了std::condition_variable来处理这种情况。
std::condition_variable是一种条件变量,可以等待一个特定的条件,并且只有当其它线程通知后才会继续执行。下面是一个示例代码:
#include <iostream>
#include <chrono>
#include <thread>
#include <condition_variable>
std::condition_variable cv;
std::mutex cv_m;
int i = 0;
void waits(){
std::unique_lock<std::mutex> lk(cv_m);
std::cout << "Waiting... \n";
cv.wait(lk, []{return i == 1;});
std::cout << "...finished waiting. i==1\n";
}
void signals(){
std::this_thread::sleep_for(std::chrono::seconds(1));
std::cout << "Notifying...\n";
cv.notify_all();
}
int main(){
std::thread t1(waits), t2(waits), t3(waits), t4(signals);
std::this_thread::sleep_for(std::chrono::seconds(5));
i = 1;
cv.notify_all();
t1.join(), t2.join(), t3.join(), t4.join();
}
在上面的示例代码中,我们创建了4个线程,分别是t1、t2、t3和t4。t1、t2和t3线程等待一个条件,即i等于1,而t4线程在程序开始运行时睡眠1秒钟,然后将i设置为1,并通知t1、t2和t3线程条件变量cv。
总结
本文介绍了如何在一个睡眠状态的std::thread中唤醒它。通过使用std::condition_variable,我们可以等待一个特定的条件,并且只有当其它线程通知后才会继续执行。这是一种非常有用的多线程编程技巧,对于一些需要使用多线程编程的需求,可以更好地实现程序的需求。