覆盖析构函数-C ++

maor36a

假设我有:

struct Base
{
    /**/ virtual /**/ ~Base() {/*..*/}
    // ...
};

struct Derived : Base
{
    ~Derived() /* override */ {/*..*/}
    // ...
};

当一个类从另一个类继承时,此处的重写可帮助我确保自己实现了中真正存在的功能Base在上述这种情况下,Derivedclass的名称不同于Base,因此其析构函数的编写方式也不同。

我的问题是,如果要使用它override,该在哪里使用?我在哪里真正实现BaseDerived类的函数?

怪异的

首先,“ override”关键字仅表示“此函数在某些基类中被标记为具有病毒性”,仅此而已。它也可以应用于析构函数。但是析构函数是特殊的,正常规则不适用于它们。对于例如析构函数Derived,命名~Derived()与析构函数匹配Base,命名~Base(),即使形式上,他们有不同的名称(或者是吗?什么是这里的名字呢?)。

析构函数与典型函数之间的另一个区别是,无论实现如何,析构函数总是在继承链中调用。因此,您不能“替换”破坏,而只能“扩展”破坏。请注意(与普通函数不同)从派生析构函数调用基类析构函数是一个错误。

链接销毁调用从您当前所指的类开始。我的意思是

Base* inst = new Derived();
delete inst;

将调用~Base(),因为变量instBase*,即使它是从一个派生类中构造。此时适用“虚拟逻辑”:如果~Base()不是虚拟逻辑,则正常的销毁过程将触发Base类,而不会意识到实际的对象是Derived*,即执行了~Base()所有其父描述符(在这种情况下没有)。错了 但是,如果它是虚拟的,那么它将实际上跳到正确的类Derived,并调用正确的销毁过程:首先是~Derived(),然后是~Base()看到这个godbolt.org 并尝试:在基本析构函数中添加和删除“虚拟”以查看区别(仅查看左列,带有彩色背景的行是实际被调用的行)。

总而言之:是的,您可以使用~Derived() override {}我总是在适当的地方使用“覆盖”,很高兴知道哪些函数是从虚函数派生的。经验法则是:如果Base是虚拟的(意味着任何函数都是虚拟的),则其析构函数也应该是虚拟的。请牢记这一点,它将帮助您避免一些问题。

本文收集自互联网,转载请注明来源。

如有侵权,请联系 [email protected] 删除。

编辑于
0

我来说两句

0 条评论
登录 后参与评论

相关文章