C++ 使用std::make_unique、std::make_shared替换new

C++11中有std::make_shared,C++14中增加了std::make_unique,它们把任意集合的参数完美转发给动态分配对象的构造函数,然后返回一个指向那对象的智能指针。那么它们与new的区别是什么呢?

auto upw1(std::make_unique<Widget>()); 
std::unique_ptr<Widget> upw2(new Widget); 
auto spw1(std::make_shared<Widget>()); 
std::shared_ptr<Widget> spw2(new Widget); 

本质上的区别是:使用new的版本需要重复创建的类型(即出现了两次Widget),而使用make函数不需要。

第二个原因异常安全。

std::make_shared的一个特点(相比于直接使用new)是提高效率。使用std::make_shared允许编译器生成更小、更快的代码。考虑当我们直接使用new时:

std::shared_ptr<Widget> spw(new Widget);

很明显这代码涉及一次内存分配,不过,它实际上分配两次。每个std::shared_ptr内都含有一个指向控制块的指针,这控制块的内存是由std::shared_ptr的构造函数分配的,那么直接使用new,需要为Widget分配一次内存,还需要为控制块分配一次内存。

如果用std::make_shared呢,

auto spw = std::make_shared<Widget>();

一次分配就够了,因为std::make_shared会分配一大块内存来同时持有Widget对象和控制块。这种优化减少了程序的静态尺寸,因为代码只需要调用一次内存分配函数,增加了代码执行的速度,因为只需要分配一次内存。而且,使用std::make_shared能避免一些控制块的信息,潜在地减少了程序占用的内存空间。

结论:

  • 相比于直接使用new,make函数可以消除代码重复,提高异常安全,而且std::make_shared生成的代码更小更快。
  • 不适合使用make函数的场合包括需要指定自定义删除器和想要传递大括号初始值。
  • 对于std::shared_ptr,使用make函数可能是不明智的场合包括(1)自定义内存管理函数的类、(2)内存紧张的系统中,有非常大的对象,然后std::weak_ptr比std::shared_ptr长寿。
  • 3
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值