c ++ vector - push_back(* new obj())和push_back(obj())之间有什么区别?

时间:2014-01-25 08:31:05

标签: c++ memory-management vector heap push-back

我目前遇到与以下问题相关的问题:

vector<myObj> myVector;

Q1。请告诉我以下两行之间的区别:

a) myVector.push_back(*new myObj());
b) myVector.push_back(myObj());

注意:我意识到a)行是不好的做法,因为它在将myObj的内容复制到向量之前动态分配myObj的内容导致内存泄漏,因此无法释放......

然而,我假设这两行都应该导致包含完全相同内容的向量,尽管看起来这个假设是不正确的。我正在使用a)开发RUNS的软件很好(我知道,我知道这会导致泄漏,请暂时忽略这一点)但是在b)行崩溃了各种不同的exc_bad_access错误。

Q2。任何人都可以解释为什么会这样吗?

编辑:发布时我最初认为我的问题必须与生成的矢量内容有所不同,但我的问题实际上与实现“三条规则”有关http://en.wikipedia.org/wiki/Rule_of_three_(C%2B%2B_programming) 感谢@WhozCraig,@ juanchopanza&amp; @Alex Antonov为您提供帮助!

3 个答案:

答案 0 :(得分:4)

  

有什么不同......

区别在于线a)导致内存泄漏,而线b)没有。这是因为a)中的动态分配对象被立即丢弃,并且没有句柄可以在其上调用delete。该向量包含并拥有其元素,在这种情况下,它是您推回其中的元素的副本。

  

我正在开发的软件使用第a行运行良好,但在b)行崩溃时出现各种不同的exc_bad_access错误。

它似乎运行正常,但它有资源泄漏。因此,任何想象力都不是很好。如果您对第b)行有疑问,可能是因为myObj管理资源而不遵循rule of three。线路b)应该适合精心设计的班级。

答案 1 :(得分:2)

在a)行中你创建了2个对象,并且你有以下方法调用:
1)第一个对象的默认构造函数
2)复制第二个对象的构造函数

在第b)行中你也创建了2个对象但是你有以下方法调用:
1)第一个对象的默认构造函数
2)第二个对象的复制构造函数
3)第一个对象的析构函数

显然,a)行是有效的,因为没有调用析构函数。这意味着很可能在行b)中你在析构函数中释放/释放一些资源(例如动态分配的内存),然后尝试通过第二个对象访问该资源。在这种情况下,您需要正确实现复制构造函数。例如。你需要在复制构造函数中分配新的内存/对象,而不是简单地将指针复制到内存/对象。

答案 2 :(得分:0)

A1:不同之处在于:(a)在堆上创建一个对象,然后取消引用它,(b)创建一个堆栈对象。

A2:由于您还需要删除堆分配的对象,因此会出现内存泄漏。 std :: vector不会为你执行此操作,因为它无法知道传递的对象是在堆还是堆栈上分配。

将对象插入向量时,将复制它。如果要保留堆分配的对象,则需要将其定义为:

std::vector<*myObj> myVector;
相关问题