纯抽象基类上的虚拟析构函数

发布于 2024-09-11 14:44:20 字数 399 浏览 6 评论 0原文

我有

struct IMyInterface
{
   virtual method1() = 0;
   virtual method2() = 0;
};

海湾合作委员会坚持认为我有

struct IMyInterface
{
   virtual method1() = 0;
   virtual method2() = 0;
   virtual ~IMyInterface(){};
};

我不明白为什么。纯接口就是关于接口的一切(废话)。析构函数是接口具体实现者的内部实现细节的一部分;它不构成界面的一部分。我理解整个切片问题(或者至少我认为我理解)

所以我的问题是 - GCC 坚持这样做是否正确,如果是的话为什么?

I have

struct IMyInterface
{
   virtual method1() = 0;
   virtual method2() = 0;
};

GCC insists that I have

struct IMyInterface
{
   virtual method1() = 0;
   virtual method2() = 0;
   virtual ~IMyInterface(){};
};

I dont see why. A pure interface is all about the interface (duh). The destructor is part of the internal implementation details of a concrete implementer of the interface; it does not form part of the interface. I understand the whole slicing issue (or at least I think I do)

So my question is - is GCC right to insist on it and if so why?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

逆夏时光 2024-09-18 14:44:20

根据 C++ 规范,是的。

您需要将析构函数声明为 virtual,因为否则,以后

    IMyInterface * ptr = getARealOne();
    delete ptr;

将不会在派生类上调用析构函数(因为析构函数不在 VTable 中)

它需要是非纯的,因为基类析构函数总是由子类调用类析构函数。

进一步解释一下,C++ 不像 Java 或 C# 那样有接口的概念。仅使用纯虚拟方法只是一种约定,并将其视为一个接口。关于 C++ 析构函数的其他规则使其必须是非纯的,这打破了与其他语言中接口的相似性,但这些语言在制定这些规则时并不存在。

According to the C++ spec, yes.

You need to declare the destructor virtual because otherwise, later

    IMyInterface * ptr = getARealOne();
    delete ptr;

won't call the destructor on the derived class (because the destructor isn't in the VTable)

It needs to be non-pure because base class destructors are always called by the sub-class destructor.

To further explain, C++ doesn't have a concept of an interface in the same way that Java or C# do. It's just a convention to use only pure-virtual methods, and think of that as an interface. The other rules about C++ destructors make it need to be non-pure, which breaks the similarity to interfaces in other languages, but those languages didn't exist at the time these rules were made.

万劫不复 2024-09-18 14:44:20

如果不在基类中声明 virtual d'tor,则通过指向基类的指针删除派生类的对象会导致调用错误的析构函数,从而导致未定义的行为和资源泄漏。

struct A {

  virtual ~A() {}

};

struct B : A {

   std::string us_constitution;  
};


B* pb = new B();
A* pa = pb;

delete pa; // without the virtual d'tor in the base class, 'B::us_constitution' would never be freed.

If you don't declare the virtual d'tor in the base class, deleting objects of derived classes through a pointer to the base class leads to the wrong destructor being called, and thus to undefined behaviour and resource leaking.

struct A {

  virtual ~A() {}

};

struct B : A {

   std::string us_constitution;  
};


B* pb = new B();
A* pa = pb;

delete pa; // without the virtual d'tor in the base class, 'B::us_constitution' would never be freed.
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文