假设有一个由主线程控制的布尔标志(keep_running)。另一个线程无限循环直到该标志变为假。应该布尔标志总是原子?
int main() {
bool keep_running(true);
std::thread run([](bool &keep_running)
{
while(keep_running)
{
// do work
}
}, std::ref(keep_running));
// do other work
keep_running = false;
run.join();
return 0;
}
该标志应该是原子吗?
std::atomic<bool> keep_running
我想,这可能发生在非原子版本最差的将是标志被正确的执行
while(keep_running)
当时间设定。在这种情况下,循环会继续运行一次(不是严格需要的)迭代。但就我而言,这是可以接受的。
上面的代码可能是错误的吗?
编辑:
我在这个性能方面的原因大多是兴趣(和没有错误)。因此,对循环中的标志使用std :: atomic是否会对性能产生负面影响?
在老版本的C++中,你会使用'volatile' - 没有它,就有可能从另一个线程看不到从一个线程写入变量。但是,因为在C++ 11中有'atomic',你应该使用它来防止相同的问题。 –
当然它应该是原子的。这给你正确的语义。你为什么要做其他事情? –
我在想,我在旗帜周围也不需要记忆障碍,也不需要关心指令重新排序。因此,我认为我可以摆脱std :: atomic来获得性能。我试图澄清,通过编辑问题。但是我没有意识到变量可能会卡在寄存器中,正如Tsyvarev在他的回答中所指出的那样。 –