这是一个强大的数据消耗回路中止选项:
while(true) {
decltype(dataContainer) data;
{
std::unique_lock<std::mutex> lock(mutex);
cond.wait(lock, []() { return stopThread || !dataContainer.empty(); });
if (stopThread)
return; //exit thread
data = std::move(dataContainer);
}
for (auto&& d:data) {
if (stopThread) return; // abort
//process data from d
}
}
stopThread
应atomic
或在底部需要有mutex
加以防护在for(:)
环路接。
在for(:)
循环中访问stopThread
是可选的;没有它,它将不会中止,直到它完成了它所拾取的一揽子工作。
dataContainer
是一组工作要做的std::vector
或某些形式的工作。线程醒来,抓住所有待完成的工作,然后开始工作。
你也可以从dataContainer
中弹出一个任务,而不是全部完成。由此产生的代码更简单。
要排队的数据为dataContainer
,你必须锁定mutex
,把数据,然后通知:
{
std::unique_lock<std::mutex> lock(mutex);
dataContainer.push_back(new_data);
}
cond.notify_one();
关闭:
{
std::unique_lock<std::mutex> lock(mutex);
stopThread = true;
}
cond.notify_all();
请注意,即使stopThread
是原子,你需要获取互斥锁。另外还有一个竞赛条件。
我知道你在使用lambdas,但是'[&] {...}'语法是什么? –
通过引用抓住一切,没有参数 –
我会做一个永久循环,等待,并打破自己。另外,你应该让你的'newDataAvailable'具有相同的名字。 ;)接下来,您可能不希望在整个处理数据期间持有互斥锁;这使得排队等待新数据的人们必须等待旧数据的处理。 – Yakk