3

将对象添加到向量与在 C++ 中添加指向向量的指针。

例子:

std::vector<Size> buildings;
Size building(buildingWidth, buildingHeight);
buildings.push_back(building);

VS

std::vector<Size*> buildings;
Size *building = new Size(buildingWidth, buildingHeight);
buildings.push_back(building);

哪一个在内存/性能方面更好?

第一个基本上在堆栈上创建一个对象并将其添加到向量中。所以有一个实例化,然后是一个副本到向量中。

第二个在堆上创建一个对象。有一个实例化,但没有复制到向量中。

我对么?

4

6 回答 6

4

这两种存储技术服务于不同的目的。

第一种技术对“同质”向量很有用,您不需要多态行为,并且对象切片不是问题。作为回报,您将获得自动化的资源管理:您无需担心对象的所有权,因为向量会生成副本。每次调整矢量大小时,也会在内部制作一个副本。当复制对象有点昂贵时,这种考虑使得第一个选项不那么有吸引力。您需要分析您的代码以查看此考虑是否适用于它。

The second technique puts the responsibility for managing the memory on you: every time you decide to remove an object from your vector of pointers, you need to take the ownership, and eventually delete the object explicitly. You can use smart pointers to address the resource management issue. This technique lets you avoid copying, but the process of accessing elements inside the container becomes slightly more involved.

于 2013-05-29T15:05:17.470 回答
0

它们通常具有相对相似的性能,具体取决于对象的大小和对象的复制语义。关于内存泄漏和可用性,第一种方法通常要好得多。

于 2013-05-29T15:00:39.993 回答
0

这实际上取决于大小的性质。如果对象很大(复制构造函数必须做很多工作),那么你可以考虑你的指针想法。但是,您必须自己控制内存,并且无论您做什么,都不要从 std::vector 继承,因为从标准容器继承不是一个好主意(一方面它们没有虚拟析构函数)!

您可以在 Size 类中构建一些关于写入语义的副本(有点像 std::string 的实现)。

或者有一个默认构造函数和一个 Size 的交换方法(无论如何你都需要在 std::vector 中使用默认构造函数)。使用 swap 方法将新的 Size 对象交换到向量中的位置。

基于“过早优化是万恶之源”(attrib. Tony Hoare),我会坚持最简单的方法;即你的第一个想法,看看它是如何进行的。

于 2013-05-29T15:05:01.580 回答
0

It really comes down to

  • What operations are going to be performed on that vector
  • How frequently objects will be pushed onto the vector

If you're going to be doing any kind of mutable operation on the vector, then you'd better go with a shared_ptr type.

Ultimately, with any kind of performance-related question, it's best to test it out yourself under the conditions of your application.

于 2013-05-29T15:05:56.570 回答
0

Why not do this:

std::vector<Size> buildings;
buildings.resize(1);
buildings[0].setSize(buildingWidth, buildingHeight);

This way the constructor is only called once, and you don't have to manage the memory yourself. The only disadvantage I can think of is that the width and height are set twice (once in constructor, once in "setSize"), but I don't think you can get away from that unless you use the std::vector<Size *> approach.

于 2013-05-29T15:08:51.540 回答
-1

I think the second approach of using vector of pointers is a better of the two options. Because of two simple reasons

  1. If the objects size are bigger then using vector of objects will add unnecessary copying.
  2. If you are passing the vector of objects as argument to a method and then try to modify any object in the vector then it will not get reflected at all the places.
于 2013-05-29T15:12:26.337 回答