从C ++容器中删除对象而不删除它们

时间:2012-11-25 10:01:55

标签: c++ stdvector 3d-engine

我正在使用C ++标准向量来存储渲染对象以进行简单的场景图实现。我需要能够在运行时从场景图中添加和删除渲染对象。添加不是问题,用于删除:读取文档向量和其他C ++容器看起来,当弹出对象时,它们的析构函数被调用。这不是我需要的,因为我希望以后能够将这些对象重新添加到渲染循环中。这个问题的可能解决方案是什么? 我忘了提到的重要细节 - 我正在使用指向渲染对象的指针向量。

3 个答案:

答案 0 :(得分:9)

您似乎对对象实例的基本概念感到困惑。向向量添加内容时,不要将其移入到向量中,复制它:

vector<string> vec;
string s;
vec.push_back(s);

vec[0] s,它是s的副本。因此,当您从向量中删除它时,s 受影响。

如果您不想要副本,则应切换到指针。你可以从向量中删除指针,并且不会调用它们指向的对象的析构函数。

编辑: 好吧,看来你已经在使用指针了。你说:

  

读取矢量和其他C ++容器的文档时,它似乎在何时   对象被弹出他们的析构函数被称为

这是事实。从向量中删除指针时,指针将被销毁。这就是文档的意思。这并不意味着指针指向的对象被破坏:

vector<string*> vec;
string s;
vec.push_back(&s);
vec.pop_back();

s完全没有受到影响。弹出操作破坏的是指针,其中包含s的地址,而不是s本身的地址。

所以你没事。

答案 1 :(得分:3)

您需要了解所有权才能使其正常运行。如果您使用的矢量只是临时的,只能观察物体,只需使用点矢量。

std::vector<object*> x;

在销毁vector时,被指向的对象不受影响。

如果您想分享所有权,请使用boost::shared_ptrstd::shared_ptr

答案 2 :(得分:2)

当弹出指针时,不会调用析构函数。理论上甚至原始类型都有析构函数,用于解释当它们超出范围时会发生什么。销毁指针向量与使一堆本地指针变量超出范围是一样的。

引用计数智能指针是使*->运算符重载以使其像指针一样运行的对象。他们确实实现了析构函数来销毁指向对象,从而实现所有权。但对于场景图,这可能是不必要的。