首页 > 解决方案 > 在析构函数中保存 std::lock_guard 是否安全?

问题描述

我正在尝试确定以下代码是否安全,或者它是否是 UB 并且仅在这种情况下运行良好(在此处运行):

#include <iostream>
#include <mutex>

struct Foo
{
  std::mutex mutex;
  ~Foo()
  {
    std::lock_guard<std::mutex> lock(mutex);
  }
};

int main() 
{
  {
    Foo foo;
  }
  std::cout << "everything seems to work fine...?" << std::endl;
}

具体来说,我们是否保证在析构函数中定义的局部变量会在成员变量之前被破坏?

我从cppreference.com找到了以下内容,但它似乎并没有完全回答我的问题:

破坏顺序

无论是用户定义的还是隐式定义的析构函数,在析构函数体执行完毕后,编译器都会为类的所有非静态非变体成员调用析构函数,按照声明的相反顺序,然后调用析构函数的析构函数。所有直接非虚拟基类以相反的构造顺序(依次调用其成员及其基类的析构函数等),然后,如果该对象属于最派生类,则它调用所有虚拟的析构函数基地。

标签: c++multithreadingdestructor

解决方案


根据 [class.dtor]/9 中的标准,

在执行析构函数的主体并销毁主体内分配的任何自动对象后,类X的析构函数调用X的直接非变体非静态数据成员的析构函数、X非虚拟直接基类的析构函数,以及, ifX是最派生类的类型(15.6.2),它的析构函数调用X的虚拟基类的析构函数。...

这肯定地回答了你的问题。


推荐阅读