创建std::shared_ptr
后不使用new
是否可以使用自定义删除器?
我的问题是对象创建是由工厂类处理的,并且其构造函数和析构函数受到保护,这会产生编译错误,并且由于其缺点,我不想使用new
。
详细说明:我更喜欢创建这样的共享指针,这不允许您设置自定义删除器(我认为):
auto sp1 = make_shared<Song>(L"The Beatles", L"Im Happy Just to Dance With You");
或者我可以这样创建它们,这确实让我可以通过参数设置删除器:
auto sp2(new Song, MyDeleterFunc);
但是第二个使用
new
,AFAIK的效率不及顶级分配。也许这更清楚:是否有可能获得
make_shared<>
和自定义删除器的好处?这是否意味着必须编写分配器? 最佳答案
在这种情况下,您必须使用new
,因为std::make_shared
的设计可以避免额外的分配,只有在std::make_shared
可以使用其自己的(内部)自定义删除器释放对象和shared_count
的组合内存的情况下,该分配才有效。
您必须接受自己的自定义删除器无法优化分配,但是出于安全使用的原因,您仍应使用类似于std::make_shared
的包装器来封装new
。这有助于避免在对象的构造函数抛出异常并且有人使用该对象的情况下发生内存泄漏。
template<typename T>
void f(const T&, const T&);
f( std::shared_ptr<X>(new X), std::shared_ptr<X>(new X) ); // possible leak
代替
std::shared_ptr<X> make_X() { return std::shared_ptr<X>(new X); }
f( make_X(), make_X() ); // no leak