我正在尝试使用抽象类来表示子类型的通用基础。但是,无论我做什么,它(似乎是链接器)都在抱怨vtables和未定义的引用。从错误消息来看,问题必须以某种方式与析构函数有关。足够有趣,它一直在谈论


“未定义对'AbstractBase :: ~~ AbstractBase()的引用”


在child.cpp中,这没有任何意义。

像上次一样,我实际上无法显示我的代码,因此这是一个实质上执行相同操作的示例:

首先是抽象类“ AbstractBase.h”:

#ifndef ABSTRACTBASE
#define ABSTRACTBASE

class AbstractBase
{
   public:
   virtual ~AbstractBase() = 0;
}
#endif


使用abstractbase“ child.h”的子级:

#ifndef CHILD
#define CHILD

class child : public AbstractBase
{
   public:
      ~child() override;
}
#endif


“ child.cpp”中的实现:

#include "child.h"
child::~child()


显然,还有更多的功能,但从本质上讲,这就是我的真实类的析构函数的外观。

在网上搜寻使用C ++中抽象类的方法之后,我将放弃。据我所知,这就是做到这一点的方法。您将抽象类的析构函数声明为虚拟的,因此对其的任何调用都将包含子类。孩子的析构函数被简单地标记为override。应该没有别的了。

我在这里错过了真正基本的东西吗?

PS:添加了MCVE:

class AbstractBase
{
   public:
   virtual ~AbstractBase() = 0;
};

class child : public AbstractBase
{
    public:
    void dostuff()
    {
      //stuff
    }

    ~child() override
    {}
}

int main (argc, char *argv[])
{
   child* ptr = new child();
   ptr->dostuff();
}


我应该补充一点,我现在得到的错误并不完全相同,而原始错误看起来像这样:


未定义对'vTable for AbstractBase'的引用:在函数中
AbstractBase:〜AbstractBase()':未定义对'vtable的引用
AbstractBase':未定义对'TypeBase for AbstractBase'的引用:
Collect2:error:ld返回1个退出状态

最佳答案

您需要为每个类定义一个析构函数,否则您将无法销毁该类的对象(包括成员对象和基础子对象):

class AbstractBase
{
public:
   virtual ~AbstractBase() = default;
}; //                     ^^^^^^^^^^^


一些替代公式:


用户自定义:

struct AbstractBase {
    virtual ~AbstractBase() {}
};

纯虚拟的,但定义如下:

struct AbstractBase {
    virtual ~AbstractBase() = 0;
};

AbstractBase::~AbstractBase() = default;


即使您没有其他虚拟成员函数,这样做的好处也是使类保持抽象。
结合两个:

struct AbstractBase {
    virtual ~AbstractBase() = 0;
};

AbstractBase::~AbstractBase() {}

07-28 12:00