std::atomic<int> g_atomic;
void thread0()
{
int oldVal = 0;
int newVal = 1;
while (g_atomic.compare_exchange_strong(oldVal, newVal, std::memory_order_acq_rel, std::memory_order_acquire))
{
// forever counting from 0 to 100 until unexpected value appears
oldVal = newVal;
newVal = (oldVal + 1) % 100;
};
}
void thread1()
{
// set unexpected value
g_atomic.store(-1, std::memory_order_release);
}
int main()
{
g_atomic.store(0);
std::thread t0(thread0);
std::thread t1(thread1);
t0.join();
t1.join();
return 0;
}
在线程0可见之前,线程1的写入是否会在线程0的循环中被覆盖吗? 该程序将永远运行。在我的测试中不会发生这种情况,但是如果有任何保证说总是如此,我会很感兴趣。
答案 0 :(得分:4)
因此,为了提供一个明确的答案,这不,从线程1写将永远不会被thread0错过。
这是因为std::atomic::compare_exchange_strong
是一个原子操作,因此从线程0进行的写入要么在该操作开始之前(在这种情况下它返回false
)要么在操作完成之后(这种情况下调用将失败)下次再循环一次。
如果采用其他方法,compare_exchange_strong
将没有实用程序,不是吗?