51

make_shared<T>()使用 using而不是 using有什么缺点吗shared_ptr<T>(new T)

Boost 文档状态

用户反复请求创建一个给定类型的对象并返回一个 shared_ptr 给它的工厂函数。除了方便和风格之外,这样的函数也是异常安全的,并且速度相当快,因为​​它可以对对象及其相应的控制块使用单个分配,从而消除了 shared_ptr 构造开销的很大一部分。这消除了关于 shared_ptr 的主要效率抱怨之一。

4

5 回答 5

38

除了@deft_code 提出的要点之外,还有一个更弱的:

  • 如果您使用在给定对象的weak_ptr所有shared_ptrs 都死了之后仍然存在的 s,那么该对象的内存将与控制块一起存在于内存中,直到最后一个 weak_ptr 死。换句话说,对象被销毁但直到最后一个对象被销毁才被释放weak_ptr
于 2010-01-27T15:41:16.503 回答
26

我知道至少有两个。

  • 您必须控制分配。真的不是一个大的,但一些较旧的 api 喜欢返回您必须删除的指针。
  • 没有自定义删除器。我不知道为什么不支持,但事实并非如此。这意味着您的共享指针必须使用普通删除器。

相当薄弱的环节。所以尽量总是使用make_shared。

于 2010-01-27T14:40:37.313 回答
14

来自http://www.codesynthesis.com/~boris/blog/2010/05/24/smart-pointers-in-boost-tr1-cxx-x0/

make_shared() 实现的另一个缺点是目标代码大小的增加。由于这种优化的实现方式,将为您使用 make_shared() 的每个对象类型实例化一个额外的虚拟表以及一组虚拟函数。

于 2011-05-10T21:43:17.540 回答
8

Additionally, make_shared is not compatible with the factory pattern. This is because the call to make_shared within your factory function calls the library code, which in turn calls new, which it doesn't have access to, since it cannot call the class's private constructor(s) (constructor(s) should be private, if you follow the factory pattern correctly).

于 2013-03-04T13:50:34.340 回答
7

使用 make shared 您不能指定如何分配释放所持有的对象。

如果需要,请std::allocate_shared<T>改用:

std::vector<std::shared_ptr<std::string>> avec; 
std::allocator<std::string> aAllocator;
avec.push_back(std::allocate_shared<std::string>(aAllocator,"hi there!"));

请注意,向量不需要被告知分配器!

要制作自定义分配器,请查看此处https://stackoverflow.com/a/542339/1149664

于 2012-11-04T09:53:14.223 回答