【问题标题】:How to use a std::lock_guard without violating const correctness?如何在不违反 const 正确性的情况下使用 std::lock_guard?
【发布时间】:2018-06-16 10:05:44
【问题描述】:

在一个子类中,我有一个私有 std::mutex m 字段,我在基类纯虚方法的实现中使用它以线程安全的方式返回一个值(该值可以由另一个线程更新):

int SubClass::get() const // implements 'virtual int get() = 0 const' of the base class
{            
    std::lock_guard<std::mutex> lck(m); 
    return value;
}

编译器告诉我这违反了 const 的正确性并产生错误:

错误:将 'const std::mutex' 绑定到类型的引用 'std::lock_guard::mutex_type& {aka std::mutex&}' 丢弃 限定词

有没有办法使其符合并以 const 正确的方式使用 std::lock_guard?只需将其更改为 const std::lock_guard 不会改变任何内容。我真的不明白哪个部分有问题,那么我对 C++ 还是很陌生...

【问题讨论】:

  • mSubClass 的成员吗?
  • 这个问题被标记为重复,但事实并非如此。要解决所谓的重复问题,答案(使用 mutable 关键字)应该是已知的......

标签: c++ multithreading constants


【解决方案1】:

this 指针隐含为const(它实际上是const SubClass * 类型的右值),因此您访问的任何成员都隐含为const

如果您可以在const 函数中修改成员对象,那么const 的意义何在? :)

锁守卫想要修改互斥体,锁定和解锁它,但是因为它是const,它不能,这就是问题所在。锁守卫是否为const 无关紧要,因为这与锁守卫修改互斥体的能力无关。

为了有效解决这个问题,有一个关键字可以用来标记const限定函数中可以修改的成员对象。现在很明显,你不应该滥用这个特性并用它来标记你类的每个对象:

class SubClass {
/*...*/
private:
    mutable std::mutex m;
  //^^^^^^^
/*...*/
}; 

【讨论】:

  • 只是挑剔(嘿,这是 C++),this 不是 const 指针。也就是说,类型仍然是const SubClass* - 它只是它的值是一个右值,所以你不能分配给它。就好像编译器提供了一个魔术宏#define this (this_ + 0),而函数的隐藏参数被命名为this_coliru.stacked-crooked.com/a/a92dbf35021f8758
猜你喜欢
  • 2022-01-10
  • 2012-09-15
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-03-29
  • 1970-01-01
  • 2016-05-04
相关资源
最近更新 更多