【问题标题】:Do I need a virtual destructor if descendant classes have no non-static members or destructors? [duplicate]如果后代类没有非静态成员或析构函数,我是否需要虚拟析构函数? [复制]
【发布时间】:2014-03-23 03:54:37
【问题描述】:
我正在使用文件描述符的类层次结构,其中基类包含一个 int 并在销毁期间对其调用 close 并且子类不添加任何虚拟方法或数据成员,只是它们的不同构造(例如named_file_filedes 采用路径并在ctor 中使用open 初始化基)或非虚拟成员函数(例如,您只能在kqueue_filedes 上调用kevent)。鉴于此,基类是否需要虚拟析构函数?子类的大小都是一样的,没有一个有自定义的销毁逻辑。标记为c++11,因为那是我所针对的标准版本。
【问题讨论】:
标签:
c++
c++11
virtual-destructor
【解决方案1】:
如果您打算通过deleteing 基类指针来销毁派生类对象,则需要virtual 析构函数。如:
class Foo {};
class Bar : public Foo {}
int main()
{
Foo* f = new Bar;
delete f; // << UNDEFINED BEHAVIOR without virtual destructor in base classe
}
如果您要求对象是多态的,您还需要在基中至少有 1 个virtual 方法——例如,如果您打算使用dynamic_cast 从基到派生。在这种情况下,通常会提供一个虚拟析构函数。只有一个虚析构函数就足以确保类是多态的。
【解决方案2】:
如果您通过指向基类的指针delete 派生类,那么无论派生类看起来如何,如果没有虚拟析构函数,行为将是未定义的。
C++11 标准,§5.3.5/3:
如果要删除的对象的静态类型与其不同
动态类型,静态类型应该是要删除的对象的动态类型的基类,并且静态类型应该有虚析构函数或者行为未定义。
但是,如果类仅在构造函数上有所不同,请考虑使用派生的替代方法,例如简单的免费函数,如create_named_file()。