动态创建Obj类对象的存储方案选择及内存管理疑问
问题解答
1. 两种存储方式的可行性
完全可以用第一种不使用new的方式存储实例,不是必须用第二种方式:
- 第一种代码里,
Obj my_obj;是在栈上创建对象,调用push_back时,vector会把这个栈对象拷贝一份到自己管理的堆内存空间中。后续即使原栈对象my_obj出作用域被销毁,vector里的副本依然有效。 - 第二种方式是存储对象指针,
new Obj在堆上创建对象,vector保存的是指向该堆对象的指针。这种方式适合需要灵活控制对象生命周期、或者避免大对象拷贝开销的场景,但绝非必须选项。
2. Obj类包含指针成员的影响
如果Obj内部有裸指针成员,且没有自定义拷贝构造函数和赋值运算符重载,会触发默认的浅拷贝,带来风险:
- 默认拷贝只会复制指针的地址值,导致原对象和vector里的副本(或多个指针指向的对象)共享同一块堆内存。
- 当其中一个对象被销毁时,会释放这块共享内存,剩下的对象里的指针就变成野指针,访问它会导致程序崩溃、触发未定义行为。
- 解决办法:要么给Obj实现深拷贝逻辑(拷贝时为指针成员重新分配内存并复制内容),要么用
std::unique_ptr/std::shared_ptr这类智能指针替代裸指针,让智能指针自动管理内存,避免手动操作的风险。
3. 第二种方式是否需要手动清理资源
是的,必须手动清理:
new创建的对象生命周期由开发者掌控,vector销毁时只会销毁存储的指针本身,不会自动调用delete释放指针指向的堆对象。如果不手动遍历vector调用delete,会造成内存泄漏。- 更推荐的替代方案是使用智能指针的vector,比如
std::vector<std::unique_ptr<Obj>>,这样当vector销毁或者元素被移除时,智能指针会自动调用delete释放对应的对象,无需手动管理内存。
内容的提问来源于stack exchange,提问作者BOOM
相关产品推荐
相关产品推荐

