c++ - 为什么 std::atomic::compare_exchange_xxx() 的预期参数不是 const &?
问题描述
我确定我即将有一个面对面的时刻,但这里有:
的原型std::atomic::compare_expected_*
是
bool compare_exchange_strong (T& expected, T val,
memory_order sync = memory_order_seq_cst) volatile noexcept;
为什么expected
不是一个const T &
?
static const handle_t INVALID_HANDLE = 0;
...
std::atomic<handle_t> handle(INVALID_HANDLE);
...
handle.compare_exchange_strong(INVALID_HANDLE, newValue);
当然交换方法不需要修改期望值?
解决方案
TL;DR:因为如果预期的参数是一个const
引用,那么compare_exchange
当交换失败时将无法修改它。
您将预期值和期望值提供给compare_exchange
。如果它发现与您提供的值不同的值,它会修改您的预期值。在这种情况下,预期值不会被您提供的期望值替换(即,它未能交换,因此您可能想再次尝试交换该值)。
通常,您希望在循环中使用这些函数,因此修改您提供的预期值是有意义的,因为它为您提供了预期值的更新版本。
考虑以下原子:
std::atomic<int> a = 7;
并且您想将 的值加倍a
:
int expected = a.load(), desired;
do {
desired = 2 * expected;
} while (!a.compare_exchange_weak(expected, desired));
在上面的代码中,如果a
在交换发生之前被另一个线程更改,则在尝试执行交换时(即失败时)用 的值expected
更新。compare_exchange
a
否则,如果在失败的情况下expected
没有被修改compare_exchange
,您将不得不a
在循环的每次迭代中加载值来更新expected
:
int expected, desired;
do {
expected = a.load(); // <-- load on each iteration
desired = 2 * expected;
} while (!a.compare_exchange_weak(expected, desired));
推荐阅读
- pyspark - fasttext 模型的错误结果
- c# - 编辑列表项线程安全?
- c# - 我面临 System.Net.WebException:“远程服务器返回错误:(400)错误请求。” 同时使用 API 来发布 XML 数据
- python - 从python中的字符串获取if子句
- python - 找到某个标签后,如何正确拆分 XML 文件(分成几个其他文件)?
- ms-access - 访问 sql 代码以将记录与前一个单元格的计算值相乘
- xml - 传递给持久化的分离实体:entities.Event
- python - 如何获取矩阵的特定行和该行的所有列?在 Python 中
- c# - 使用 Newtonsoft 简化对象的反序列化
- c++ - if 语句在 Nucleo64 上不起作用,但在 Maple mini 上起作用