如何正确清理矢量/地图?
Posted
技术标签:
【中文标题】如何正确清理矢量/地图?【英文标题】:How to clean up a vector/map properly? 【发布时间】:2010-06-17 13:13:59 【问题描述】:如果我有vector<string*> *vect
或map<pair<string*, int*>, string*> *map
,
如何清理所有内容(包括矢量/地图包含的所有对象)?
(所有 (vector, map, contents, string, ints) 都用new
分配)
这就够了:
delete vect;
delete map;
【问题讨论】:
为什么要在容器中存储指针?尤其是 int* 很可能是错误的。 @Rudi:哦,我是 C++ 新手。它有什么问题? int* 只是浪费性能而没有任何好处,但即使是 string* 也意味着手动管理创建和删除,以及其中隐含的风险。只需使用字符串和整数,您的删除操作就会为您整理好一切 @Martijn Courteaux:在几乎所有现代建筑中,int*
将占用与int
一样多的空间,甚至更多。更不用说原始指针带来的痛苦了。除非绝对需要,否则避免在 C++
中使用指针。
@David & ereOn:感谢您的解释。
【参考方案1】:
不,您必须遍历vector
/map
,逐一删除和删除其项目(正如@SB 指出的那样,这可能需要递归地处置其成员)。
(您可以通过简单地删除项目来逃脱,如果您绝对确定在矢量被删除之前没有人会再访问矢量元素 - 但它是在删除之前删除每个项目会更安全。这可以确保程序在任何时候都是正确的,消除了细微错误的可能性并简化了长期维护。)
顺便说一句,这是建议将智能指针存储在集合中而不是原始指针的原因之一。
【讨论】:
人们非常喜欢使用智能指针,以至于他们经常忽略提升指针容器。它们是为这种确切的场景而设计的。 +1 用于回答问题并指出智能指针可以解决此问题。【参考方案2】:你真的应该考虑使用智能指针。
vector<boost::shared_ptr<std::string> >* some_vector = new std::vector<boost::shared_ptr<std::string> >;
some_vector->push_back(boost::shared_ptr<std::string>("Hello World !"));
delete some_vector; // This will delete the contained std::string's as well
some_vector = NULL;
基本上,一个智能指针负责所指向数据的生命周期。他们甚至可以做更多事情(例如计数引用等),但我建议您阅读this page 以了解更多关于不同类型的智能指针。
您甚至可以指定要使用的自定义“释放”函数,而不是默认函数 (delete
)。
【讨论】:
顺便提一下,既然你说你是C++
的新手:如果你曾经尝试过我的代码:两个>
之间的空格不是我编码风格的一部分:它是需要,因此编译器不会将两个 >
解释为 >>
运算符。如果你使用C++0x
,没关系。【参考方案3】:
不,您必须手动遍历每个容器并对其包含的指针调用 delete。该向量没有分配该内存,因此它不会为您清理它。
如果您使用智能指针,那么指针本身将处理释放它的内存。否则,您必须平衡手动分配和手动解除分配。
【讨论】:
【参考方案4】:您可能需要考虑Boost Pointer Container。它处理所有的清理工作,根据我的经验,普通容器可以无缝地(意味着不破坏代码)被这些容器替换。
指针容器表示容器对所包含对象的所有权,这就是您在此处所拥有的(否则您不必清理它)。
智能指针的容器是不同的,因为对象的寿命可能比容器长。此外,使用智能指针时可能会有一点性能损失,但这实际上取决于容器的大小以及对它们执行的操作类型。
【讨论】:
以上是关于如何正确清理矢量/地图?的主要内容,如果未能解决你的问题,请参考以下文章