【问题标题】:Delete dynamic polymorphic object allocated with placement new删除使用新位置分配的动态多态对象
【发布时间】:2016-04-15 04:42:18
【问题描述】:

有两个类A&B,B派生自A。A&B有虚析构函数。我还有两个放置新功能:

void* operator new (std::size_t size, const char* file, int line)
void* operator new[](std::size_t size, const char* file, int line) 

和两个放置删除功能:

void operator delete (void* p, const char* file, int line)
void operator delete[](void* p, const char* file, int line)

问题是,如果我有包含对象 A 或对象 B 的向量,我如何正确销毁向量中的所有元素?

问题是放置删除没有删除表达式。我不能调用默认的删除表达式,因为我需要提供文件和行参数,所以我坚持直接调用运算符删除,我刚刚发现这样做不会调用对象的析构函数。我也不能显式调用析构函数,因为向量内的对象可能是 A 或 B。

编辑

我尝试做v[i]->~A();,但即使向量中有一个 B 对象,也没有调用 B 的析构函数

我用这样的东西填充了向量:

v[0] = new(__FILE__, __LINE__) A;
A* temp = new(__FILE__, __LINE__) B;
v[1] = temp;

谢谢

【问题讨论】:

  • 当您使用虚拟析构函数手动调用基类指针上的析构函数时,我很确定它会正确地动态调度。
  • 向量不能包含 A 或 B。向量只能包含一种类型的元素。
  • @KerrekSB 似乎 stackoverflow 无法正确显示矢量。我写了vector,但它显示了vector。不知道为什么
  • 使用你的编辑能力,卢克。帮助中心有关于 Stack Overflow 的 markdown 语法的文档,实时预览让您在提交问题之前验证它是否符合预期...
  • 请显示有关如何填充向量的代码。

标签: c++ polymorphism placement-new


【解决方案1】:

我相信您的问题可以简化。它归结为解决以下问题:给定

A * p = new ("foo", 1) A(/* args... */);
A * q = new ("bar", 2) B(/* args... */);

您如何解除所有依附的所有权责任?

首先,您必须销毁对象:

p->~A();
q->~A();

感谢虚拟析构函数,这没问题。

现在您必须释放存储空间。你如何做到这一点取决于你的placement-new分配函数到底是做什么的!例如,如果您有:

void * operator new(std::size_t n, const char *, int)
{
    return std::malloc(n);
}

然后你必须使用std::free(p); std::free(q); 来释放内存。如果您的实现改用return ::operator new(n),那么您可以使用::operator delete(p) 等释放。如果您返回一个指向静态内存的指针,那么您不必释放任何东西。

既然你是调用placement-new分配函数的人,那你就知道怎么清理了!

【讨论】:

  • 我不能调用 p->~A() 和 q->~B() 因为我丢失了 p & q 类型的信息(并且向量正在动态扩展)。我想我可以使用额外的存储空间来保持他们的类型。但是有没有办法在不跟踪类型的情况下做到这一点?
  • @bysreg:对不起,我是说q->~A()
猜你喜欢
  • 1970-01-01
  • 2012-11-06
  • 2014-02-28
  • 2011-07-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多