如果您总是将其存储在shared_ptr中,您的接口是否需要虚拟析构函数?

发布于 2024-11-19 08:44:12 字数 531 浏览 3 评论 0原文

由于 boost::/std::shared_ptr 具有类型擦除其删除器的优势,因此您可以做一些不错的事情,例如

#include <memory>

typedef std::shared_ptr<void> gc_ptr;

int main(){
  gc_ptr p1 = new int(42);
  gc_ptr p2 = new float(3.14159);
  gc_ptr p3 = new char('o');
}

由于保存了正确的删除器,这将正确删除所有指针。

如果您确保接口的每个实现始终都是使用 shared_ptr(或 make_shared)创建的,那么您真的需要一个 virtual代码> 析构函数?无论如何,我都会声明它是虚拟的,但我只是想知道,因为shared_ptr将始终删除它初始化的类型(除非给出另一个自定义删除器)。

Since boost::/std::shared_ptr have the advantage of type-erasing their deleter, you can do nice things like

#include <memory>

typedef std::shared_ptr<void> gc_ptr;

int main(){
  gc_ptr p1 = new int(42);
  gc_ptr p2 = new float(3.14159);
  gc_ptr p3 = new char('o');
}

And this will correctly delete all pointer thanks to the correct deleter being saved.

If you ensure that every implementation of your interface always gets created with shared_ptr<Interface> (or make_shared<Interface>), do you actually need a virtual destructor? I would declare it virtual anyways, but I just want to know, since shared_ptr will always delete the type it was initialized with (unless another custom deleter is given).

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

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

发布评论

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

评论(1

东风软 2024-11-26 08:44:12

我仍然会遵循派生类的通用规则:

提供公共虚拟析构函数或受保护的非虚拟析构函数

原因是您无法控制所有用途,并且这个简单的规则意味着如果您尝试通过错误的方式删除,编译器将进行标记层次结构中的级别。考虑到 shared_ptr 不保证它将调用适当的析构函数,仅保证它将调用用作参数的静态类型的析构函数:

base* foo();
shared_ptr<base> p( foo() );

如果 base 有一个 public非虚拟析构函数并且 foo 返回派生自 base 的类型,则 shared_ptr 将无法调用正确的析构函数。如果base的析构函数是virtual的,那么一切都会好起来的,如果它是protected的,编译器会告诉你那里有错误。

I would still follow the common rule for classes that are meant to be derived:

Provide either a public virtual destructor or a protected non-virtual destructor

The reason is that you cannot control all of the uses, and that simple rule means that the compiler will flag if you try to delete through the wrong level in the hierarchy. Consider that shared_ptr does not guarantee that it will call the appropriate destructor, only that it will call the destructor of the static type that was used as argument:

base* foo();
shared_ptr<base> p( foo() );

If base has a public non-virtual destructor and foo returns a type that derives from base, then shared_ptr will fail to call the correct destructor. If the destructor of base is virtual, everything will be fine, if it is protected, the compiler will tell you that there is an error there.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文