在C ++中,我们可以在头文件中完美地声明一个函数,而无需实际实现它。这编译很好,通常这并没有提供任何问题,但是......我想知道当没有实现虚拟析构函数时它是否会导致问题。
当没有实现虚拟析构函数时,在这种情况下我们通过基类的指针删除派生类的实例,派生类的析构函数是否仍然会被调用?
E.g。
class Base{
public:
virtual ~Base() {}
};
class Derived: public Base {
public:
~Derived(); // HAS NO IMPLEMENTATION
};
Base *b = new Derived();
delete b;
注意:如评论中所述,上述示例未正确链接。这里提供的是解释我试图获得更多洞察力的情况,但是在链接过程中的实践中,此示例将导致undefined reference to Derived
错误。
答案 0 :(得分:6)
如果您曾致电~Derived()
(例如删除b
),您将收到链接错误,因为析构函数的符号不存在。由于~Base()
是虚拟的,因此删除~Derived()
时仍会(尝试)调用b
。没有实施与此无关。
答案 1 :(得分:4)
声明虚拟析构函数但没有实现时会发生什么?
如果调用析构函数(例如在您的示例中),则程序违反了一个定义规则,因此格式错误。标准不需要诊断,编译器将无法判断是否有任何错误。但幸运的是,你可能会被链接器错误保存。
在C ++中,我们可以在头文件中完美地声明一个函数,而无需实际实现它。
这是事实。但是我们不能称之为这样的功能。
虚拟和析构函数与问题无关。这些规则适用于所有功能。