【问题标题】:An error when you override non-virtual-function in C++在 C++ 中覆盖非虚拟函数时出错
【发布时间】:2011-12-19 23:12:47
【问题描述】:

当你在一个没有虚函数的类中重写一个不是虚函数的成员函数时,VS 编译器会出现“_BLOCK_TYPE_IS_VALID”错误。

例如,

class A{
public:
    int a;
public:
    void func(){}
    ~A(){}
};

class B : public A{
public:
    virtual void func(){}

    ~B(){}
};

int main(void){
    A* a = new B();
    delete a;  // error!

    return 0;
}

我猜这是因为在 main() 中,a 有 vtable 但编译器错过了它并且无法获得标头的确切大小?

谁能让我对这件事的好奇心破灭?

提前致谢。

【问题讨论】:

  • A 没有 vtable,因为其中没有虚函数。 A 是一个 POD 类。
  • @jmucchiello A 有一个用户定义的析构函数,因此它不符合 POD 的条件。不过,关闭。

标签: c++ virtual


【解决方案1】:

您可以删除A::func(),程序仍然有错误。

真正的原因是A::~A()(不是B::~B())在B 类型的对象上被调用。

C++ FAQ § 20.7“我的析构函数什么时候应该是virtual?”

【讨论】:

  • 谢谢,但是如果我让 A::~A() 相同,并将 void func() 更改为 virtual void func() 会怎样?然后错误消失了,这就是我没有从 A 类中删除 A::func() 的原因。
  • @YayCplusplus:纯粹是内存布局的意外。它仍然是未定义的行为。
【解决方案2】:

您正在尝试使用指向基类的指针来销毁对象,但析构函数不是虚拟的。如果一个类是继承层次结构的一部分,总是将 dtors 设为虚拟。

【讨论】:

  • 好吧,如果你从不调用错误的析构函数,非虚拟析构函数就可以了。但这里不是这样。
猜你喜欢
  • 2021-03-27
  • 1970-01-01
  • 2011-11-23
  • 2018-01-28
  • 1970-01-01
  • 1970-01-01
  • 2012-06-19
  • 2015-06-17
  • 2015-04-20
相关资源
最近更新 更多