什么是比较和交换有益?

Sta*_*hev 14 c c# assembly thread-safety compare-and-swap

我最近在阅读有关Compare和Swap原子动作(CMPXCHG,.NET的Interlocked.CompareExchange,无论如何).

我理解它是如何在内部工作的,以及如何从客户端使用它.

我无法弄清楚的是,何时会有人使用CAS?

维基百科说:

CAS用于实现信号量和互斥量等同步原语,同样是更复杂的无锁和无等待算法.

那么,任何人都可以给我一个更通用的真实世界用例,其中包含CAS使用的代码和描述吗?

这个问题与语言无关,因此任何语言都可以(基于C语言或x86程序集首选).

谢谢!

usr*_*usr 8

这很容易通过例子看到.假设我们想要原子地同时在共享变量上设置一点:

int shared = 0;

void Set(int index) {
 while (true) {
  if (Interlocked.CompareExchange<int>(ref shared, shared | (1 << index), shared) == shared)
   break; //success
 }
}
Run Code Online (Sandbox Code Playgroud)

如果我们看到"旧值"(即返回值)在此期间发生了变化,我们会检测到失败.

如果没有发生这种情况,我们没有进行并发修改,因此我们自己的修改成功完成.

你可以用这种技术实现相当复杂的东西.但是,通过旋转,性能损失越大越复杂.

我想强调CAS的一个关键属性是它可能会失败并且可以可靠地检测到故障.

  • 我认为你可以用这个来实现任意函数"F(共享)".在我的例子中,F(共享)是"共享|(1 <<索引)".你可以放任何东西,包括函数调用.它仍然是原子的.但是你需要知道循环可以旋转多次,所以你的函数应该可以被多次调用. (2认同)

Dav*_*ble 5

您使用CAS在一个线程或进程中原子地设置一个值(一个位或一个单词),同时测试另一个线程/进程尚未这样做.所以它用于在多线程环境中获取标志或计数器.

  • @ kubal5003 - 这特别适用于多核,因为它保证了对单词的原子(单CPU /线程/核心)访问. (2认同)