C++中以右值形式实例化的lock_guard能否正常工作?
结论:你的判断完全正确,该改动会彻底破坏线程安全性
你的分析精准命中了问题核心:
- 栈上的左值对象(如
C one;)会在当前作用域结束时按逆序销毁;但临时右值对象(如C{};)的生命周期仅持续到当前完整表达式结束,执行完这行代码就会立即被销毁。 std::lock_guard是典型的RAII工具:构造时锁定传入的互斥量,析构时自动解锁。当写成std::lock_guard{mutex};时,这个临时右值对象在构造完成、锁定互斥量后,会立刻析构并解锁——这意味着后续代码完全处于无保护状态,线程安全直接失效。
正确写法对比
C++14标准写法:
std::lock_guard<std::mutex> guard(mutex);显式声明左值对象,生命周期覆盖当前作用域,正确保护后续代码。
C++17简化写法(安全):
std::lock_guard guard(mutex);利用模板实参推导(CTAD)省略模板参数,但本质仍是左值栈对象,生命周期正常,不会有问题。
额外说明
如果非要用花括号初始化语法且保留正确生命周期,可将临时对象绑定到左值引用:
auto&& guard = std::lock_guard{mutex};
但这种写法完全没必要,反而降低可读性,不如直接使用常规的左值声明。
内容的提问来源于stack exchange,提问作者Thomas W.
相关产品推荐
相关产品推荐

