Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/161.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 将对象推回向量内存问题C++;_C++_Memory_Vector - Fatal编程技术网

C++ 将对象推回向量内存问题C++;

C++ 将对象推回向量内存问题C++;,c++,memory,vector,C++,Memory,Vector,这里比较初始化对象向量的两种方法 1. vector<Obj> someVector; Obj new_obj; someVector.push_back(new_obj); 2. vector<Obj*> ptrVector; Obj* objptr = new Obj(); ptrVector.push_back(objptr); 1。 向量someVector; Obj new_Obj; 一些向量。推回(新对象);

这里比较初始化对象向量的两种方法

1.
    vector<Obj> someVector;
    Obj new_obj;
    someVector.push_back(new_obj);

2.
    vector<Obj*> ptrVector;
    Obj* objptr = new Obj();
    ptrVector.push_back(objptr);
1。
向量someVector;
Obj new_Obj;
一些向量。推回(新对象);
2.
向量向量向量机;
Obj*objptr=新的Obj();
ptrVector.push_back(objptr);
第一个将实际对象而不是对象的指针推回。vector push_back是否复制了正在推送的值?我的问题是,我有巨大的对象和很长的向量,所以我需要找到一个最好的方法来节省内存

  • 第二条路更好吗
  • 有没有其他方法可以让对象/指针向量在以后找到每个对象并同时使用最少的内存

如果您的
Obj
类不需要多态行为,那么最好直接将
Obj
类型存储在
向量中

如果将对象存储在
vector
中,则您将承担在不再需要这些对象时手动释放这些对象的责任。在这种情况下,如果可能的话,最好使用
vector
,但同样,只有在需要多态行为时才使用

vector
将把
Obj
对象存储在堆上(默认情况下,除非覆盖
vector
模板中的
allocator
)。这些对象将存储在连续内存中,这也可以根据您的用例提供更好的缓存位置

使用
向量
的缺点是频繁插入/删除
向量
可能会导致重新分配和复制对象。然而,这通常不会成为应用程序中的瓶颈,如果您觉得它是瓶颈,那么您应该对其进行分析


使用C++11,可以大大减少复制的影响。

如果您的
Obj
类不需要多态行为,那么最好直接将
Obj
类型存储在
向量中

如果将对象存储在
vector
中,则您将承担在不再需要这些对象时手动释放这些对象的责任。在这种情况下,如果可能的话,最好使用
vector
,但同样,只有在需要多态行为时才使用

vector
将把
Obj
对象存储在堆上(默认情况下,除非覆盖
vector
模板中的
allocator
)。这些对象将存储在连续内存中,这也可以根据您的用例提供更好的缓存位置

使用
向量
的缺点是频繁插入/删除
向量
可能会导致重新分配和复制对象。然而,这通常不会成为应用程序中的瓶颈,如果您觉得它是瓶颈,那么您应该对其进行分析

使用C++11,可以大大减少复制的影响。

如果可以提前保留大小,则使用
向量将占用更少的内存<如果不需要重新分配向量,代码>向量
将必然比
向量
使用更多的内存,因为您有指针的开销和动态内存分配的开销。但是,如果您只有几个大对象,则此开销可能相对较小

但是,如果内存即将耗尽,如果无法提前保留正确的大小,则使用
vector
可能会导致问题,因为在重新分配向量时,您将暂时需要额外的存储空间

拥有大型对象的大型向量也可能导致内存碎片问题。如果您可以在程序执行的早期创建向量并保留大小,这可能不是问题,但如果稍后创建向量,您可能会由于堆上的内存漏洞而遇到问题。

如果您可以提前保留大小,则使用
向量将占用更少的内存<如果不需要重新分配向量,代码>向量
将必然比
向量
使用更多的内存,因为您有指针的开销和动态内存分配的开销。但是,如果您只有几个大对象,则此开销可能相对较小

但是,如果内存即将耗尽,如果无法提前保留正确的大小,则使用
vector
可能会导致问题,因为在重新分配向量时,您将暂时需要额外的存储空间


拥有大型对象的大型向量也可能导致内存碎片问题。如果您可以在程序执行的早期创建向量并保留大小,这可能不是问题,但如果稍后创建向量,您可能会由于堆上的内存漏洞而遇到问题。

在上述两个选项中,第三个未包含的选项是最有效的:

std::vector<Obj> someVector;
someVector.reserve(preCalculatedSize);
for (int i = 0; i < preCalculatedSize; ++i)
  someVector.emplace_back();
这可能是最好的。这里,我们表示数据的生命周期,以及如何在相同的结构中以几乎零的开销访问数据,以防止数据失去同步

要移动时,必须显式地移动
std::unique\u ptr
。如果出于任何原因需要原始指针,
.get()
是如何访问它的
->
*
显式运算符bool
都被重写,因此当您有一个需要
Obj*
的接口时,您只需要调用
.get()

这两种解决方案都需要C++11。如果您缺少C++11,并且对象确实很大,那么“数据指针向量”是可以接受的


在任何情况下,您真正应该做的是确定哪一个与您的模型最匹配,检查性能,并且只有在出现实际性能问题时才进行优化。

在上述两个选项中,第三个未包含的选项是最有效的
std::vector< std::unique_ptr<Obj> > someVector;
std::unique_ptr<Obj> element( new Obj );
someVector.push_back( std::move(element) );