背景
普通创建shared_ptr
的方法如:
shared_ptr<int> sp1(new int(11));
sp1所开辟的动态内存分为如下两部分
uses
是持有该资源shared_ptr
数量,weaks
表示持有该资源weak_ptr
数量。
有可能出现 new int(10)
成功,但是引用计数 ref
的内存空间分配或对象构造失败,此时就会造成内存泄漏问题。
make_shared
make_shared
把需要托管的内存资源和存储引用计数的内存资源一起开辟在一块内存上,要么全成功,要么全失败,可以防止构造失败时,内存泄漏,使用方法如下:
shared_ptr<int> sp3 = make_shared<int>(10);
内存示意图如下:
其他使用例子:
class Test
{
public:
Test(int a) { cout << "Test(int)" << endl; }
Test(int a, int b) { cout << "Test(int, int)" << endl; }
};
int main()
{
auto sp4 = make_shared<Test>(10); // new Test(10);
auto sp5 = make_shared<Test>(10, 5); // new Test(10, 5);
return 0;
}
优点:
内存分配效率高;
防止资源泄漏;
缺点:
make_shared
无法自定义删除器;
导致托管资源延迟释放。即引用计数中uses
(持有该资源shared_ptr
数量) 和 weaks
(持有该资源weak_ptr
数量)有一个不为0,整个内存资源(托管资源和引用计数)就都不能释放;
而用普通的方法 shared_ptr<int> p1(new int (10));
在uses为0时可以释放托管的内存资源
注:还有
make_unique
也是类似道理