c++ - 在 C++ 的析构函数中允许做什么?

标签 c++ destructor

我试图了解在析构函数中允许做什么。
standard说:“对于具有非平凡析构函数的对象,在析构函数完成执行后引用该对象的任何非静态成员或基类会导致未定义的行为”。
cppreference以这种方式描述析构序列:“对于用户定义的或隐式定义的析构函数,在执行析构函数的主体后,编译器为类的所有非静态非变体成员调用析构函数”。
这是否意味着,在以下代码中,从其成员的析构函数调用方法是 UB?或者通过“引用”标准意味着某些特定的东西?

struct Foo {
  Foo(Callback cb) : cb_(cb) {}

  ~Foo() {
    // body of Bar destructor finished at this moment;
    // cb_() calls Bar::call_me()
    cb_();
  }

  Callback cb_;
};

struct Bar {
  // pass callback with captured this
  Bar() : foo_([this]() { call_me(); }) {
  }

  void call_me() {
  }

  // foo is a member, its destructor will be called after Bar destructor
  Foo foo_;
};
另外,标准中的“析构函数完成后”这句话到底是什么意思?在析构函数的主体完成之后?还是在所有成员和基类都被销毁之后?
我认为最后一个问题的答案是理解什么是允许的,什么是不允许的关键。

最佳答案

Bar 的析构函数还没说完,所以指的是Bar的一个成员,并且确实调用了 Bar 的成员函数在其析构函数中是可以的。
但是,调用 super 对象的成员函数可能有点不稳定,因为成员函数可能会访问子对象,而在调用成员函数时,某些子对象可能已经被销毁,在这种情况下,访问被销毁的对象将导致在未定义的行为中。在您的示例中,情况并非如此。

Or by "referring" standard means something particular?


我认为这意味着形成对子对象的指针或引用。正如在规则下面的示例中所做的那样。

Also, what does the phrase "after the destructor finishes" from the standard mean exactly? After the body of a destructor finishes? Or after all members and base classes destroyed?


后者。
首先执行主体,然后析构函数调用子对象析构函数,然后析构函数完成。

关于c++ - 在 C++ 的析构函数中允许做什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/67584695/

相关文章:

c++ - boost.Geometry 运算符

c++程序寻找猜谜游戏的解决方案

c++ - 返回类析构函数

c++ - Delete[] 没有调用元素析构函数

c++ - 重新分配变量时,不调用析构函数.. (C++)

c++ - 析构函数的奇怪行为

c++ - 编译时输出一个模板类名

c++ - XCode 8 链接器 (ld) 抑制警告

c++ - 读取 BMP 文件返回意外数据

c++ - 在元素自身的析构函数中删除指向静态 vector 中元素的指针