C ++:错误的析构函数被调用

时间:2016-02-03 05:53:18

标签: c++ destructor

ProjectileNode的子类。 我希望调用Projectile析构函数。

注意:在现实场景中,我有一个Node*ProjectilePlayer的{​​{1}}列表,每个列表都有自己的析构函数。

EnemyNode中没有指定的析构函数(我假设它使用默认的析构函数。)

.h file

4 个答案:

答案 0 :(得分:4)

首先,从您的问题中可以清楚地看出NodeNode子类(请参阅this Wikipedia entry)。

如果你有一个类为class Node { ... virtual ~Node(); }; 的类是为子类化而构建的,那么你应该确保它的析构函数是虚拟的:

s destructor when you

这将导致编译器调用适当的类{{1}} delete`指向超类的指针。

(另一个问题是它是否应该是纯虚拟的。)

答案 1 :(得分:2)

你必须使Node的析构函数为virtual,默认的(非虚拟的)不满足这里的需求,即动态多态不起作用。

class Node {
public:
    virtual ~Node() {}
}

答案 2 :(得分:2)

C ++是静态类型语言,因此从此语句Node* p = new Projectile();编译器将p视为Node的对象。在破坏p时,它只会调用类Node的析构函数。

为了克服这种情况,virtual出现了。

代码:

class Node {
  public:
    virtual ~Node() {
      //delete resources allocated in Node class
    }
};

class Projectile : public Node {
  public:
    ~Projectile() {
       //delete resources allocated in Projectile class
     }
};

答案 3 :(得分:0)

简短回答:

将您的析构函数设置为Node虚拟。

class Node {
  // Stuff...
  virtual ~Node();
};

不那么简短的回答:

Projectile和那些继承Node时,数据成员和函数都是从Node继承的。派生类可以覆盖或替换父类中的实际函数定义。这种重写发生在编译时或运行时,具体取决于天气,基类中的函数被声明为“虚拟”。

在非虚拟析构函数的情况下,要调用的析构函数由指针类型决定。因此,即使指针变量p指向Projectile的实例,delete(p)也会调用Node中定义的析构函数。

在虚拟析构函数的情况下,要在运行时确定要调用的析构函数。因此,无论指针类型如何,被调用的析构函数都将是p指向的对象中定义的析构函数。