本地抽象类的纯虚拟析构函数

Pure virtual destructor of a local abstract class

本文关键字:虚拟 析构函数 抽象类      更新时间:2023-10-16

请考虑以下代码:

struct  A {
    virtual void foo() {}
    virtual ~A() = 0;
};
struct B :public A
{
    virtual void foo() {};
};
A::~A() {}; 
int main()
{
    A * a = new B();
    a->foo();
}

但是现在考虑第二个代码,我们需要在函数中本地声明我们的类为:

void foo()
{
    struct  A {
        virtual void foo() {}
        virtual ~A() = 0;
    };
    struct B :public A
    {
        virtual void foo() {};
    };
    A::~A() {}; //error C2352 : 'A::~A' : illegal call of non - static member function
    A * a = new B();
    a->foo();
}
int main()
{
    foo();  
}

代码剂量不编译! 知道吗? 有什么方法可以重新定义本地声明的基类的纯虚拟析构函数吗?

cppreference 说

声明可以出现在函数主体中(...),在这种情况下,它定义一个本地类

局部类的成员函数必须完全在类体内定义

没有办法做你想做的事。但是,还要考虑一下:为什么你通常要为纯虚拟析构函数给出一个主体定义?典型的答案是,你想使类抽象,但没有其他方法可以成为纯虚拟的。出现这种情况的情况通常是您无法直接控制类的使用或继承。但是对于在函数内部本地定义的类来说,这永远不会发生:根据定义,它的任何使用都必须在完全相同的函数体内,让作者完全控制用法。因此,例如,你可以确保你的类总是继承自而不是按原样使用(即强制类是抽象的目的),只需在本地函数的直接控制的上下文中自己观察这个规则。

在C++中,你不能有嵌套函数。通过做

foo(){
//...
A::~A{} // you define a nested function which is not allowed
//...
}

IMO,对于带有函数的嵌套类,我们必须在类块中定义所有非纯函数。

如果你想让你的类 A 是抽象类,你可以将 A::foo() 声明为纯虚拟函数或一些新的空函数。在任何情况下,您都需要在类块外部或内部定义虚拟 dtor,因为不这样做会导致链接错误。