c++智能指针用法

目录

目录

一、介绍

二、应用场景

1.shared_ptr

2.unique_ptr

3.weak_ptr


shared_ptr和weak_ptr用法

 C++智能指针循环引用问题分析_swings_ss的博客-CSDN博客

一、介绍

智能指针一共有4个,分别是shared_ptr,unique_ptr,weak_ptr,auto_ptr,最后一个被弃用了,主要是前面三种。

作用是自动回收内存,不需要是delete,原理是智能指针内部有个计数器,每当创建一次对象计数加一,销毁一次计数减一,当计数等于0时自动释放对象。

二、应用场景

1.shared_ptr

多个指针可以指向同一个对象

2.unique_ptr

一个指针只能指向一个对象

#include <iostream>

using namespace std;

class A;
class B;

class B {
public:
	B() {
		cout << "执行B类的构造函数\n";
	}
	~B() {
		cout << "执行B类的析构函数" << endl;
	}
public:
	unique_ptr<A>a;
};

class A {
public:
	A() {
		cout << "执行A类的构造函数\n";
	}
	~A() {
		cout << "执行A类的析构函数" << endl;
	}
public:
	unique_ptr<B>b;
};

int main()
{
	unique_ptr<B>pb(new B);
	unique_ptr<A>pa(new A);
	//pb->a = pa; //此时会报错

	return 0;
}

3.weak_ptr

不能增加或减少shared_ptr的计数,只能对其计数进行访问。 

为了解决循环引用导致对象不能通过shared_ptr释放,例如A类包含B类,B类又包含A类,创建后A和B的智能指针计数都为2,释放的时候两个类计数器都为1,不能自动释放,造成内存泄漏。

#include <iostream>

using namespace std;

class A;
class B;

class B {
public:
	B() {
		cout << "执行B类的构造函数\n";
	}
	~B() {
		cout << "执行B类的析构函数,类A的引用计数为:" << a.use_count() << endl;
	}
public:
	shared_ptr<A>a;
};

class A {
public:
	A() {
		cout << "执行A类的构造函数\n";
	}
	~A() {
		cout << "执行A类的析构函数,类B的引用计数为:" << b.use_count() << endl;
	}
public:
	shared_ptr<B>b;
};

int main()
{
	shared_ptr<B>pb(new B);
	shared_ptr<A>pa(new A);
	pb->a = pa;
	pa->b = pb;
	//输出pb,pa的计数个数
	cout << "pb的计数:" << pb.use_count() << endl;
	cout << "pa的计数:" << pa.use_count() << endl;

	return 0;
}

此时结束后,每个智能指针计数减一,但是pa和pb的计数减为1,不等于0,因此帮你执行delete,也就不能执行析构函数,所以不能正常释放对象pa,pb,从而造成了内存泄漏。为了解决不能正常释放对象的问题,可以在类A或者类B里使用weak_ptr,它不影响指针的引用计数。

#include <iostream>

using namespace std;

class A;
class B;

class B {
public:
	B() {
		cout << "执行B类的构造函数\n";
	}
	~B() {
		cout << "执行B类的析构函数,类A的引用计数为:" << a.use_count() << endl;
	}
public:
	shared_ptr<A>a;
};

class A {
public:
	A() {
		cout << "执行A类的构造函数\n";
	}
	~A() {
		cout << "执行A类的析构函数,类B的引用计数为:" << b.use_count() << endl;
	}
public:
	weak_ptr<B>b;
};

int main()
{
	shared_ptr<B>pb(new B);
	shared_ptr<A>pa(new A);
	pb->a = pa;
	pa->b = pb;
	//输出pb,pa的计数个数
	cout << "pb的计数:" << pb.use_count() << endl;
	cout << "pa的计数:" << pa.use_count() << endl;

	return 0;
}

 因为A类里B成员是weak_ptr,所以不增加B类的引用计数,pb=1,程序结束后,计数减一,pb=0,此时在正常执行B类的析构函数,执行B类析构函数的时候,释放B类的成员A,所以A类就似乎减一,pa此时等于1,接着执行释放A类,pa继续减一,pa=0,pb=0.

  • 0
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
智能指针是一种重要的C++特性,它可以帮助程序员管理动态分配的内存,以防止内存泄漏和悬挂指针等问题。 智能指针用法非常简单,程序员只需要包含<memory>头文件,并使用std::shared_ptr、std::unique_ptr或std::weak_ptr等类来创建智能指针对象。 其中,std::shared_ptr是最常用的一种智能指针,它可以实现多个智能指针共享同一块内存。当最后一个shared_ptr离开其作用域时,内存会被自动释放。 std::unique_ptr是一种独占式智能指针,它不能被复制,只能通过移动语义传递到其他unique_ptr中。这样可以确保在内存释放时不会出现问题。 std::weak_ptr是一种弱引用智能指针,它可以用于解决循环引用问题。weak_ptr不会增加引用计数,但可以通过lock()方法获取一个shared_ptr来访问它所管理的对象。 使用智能指针的好处是它们可以自动管理内存释放,避免因忘记释放内存而导致的内存泄漏问题。此外,智能指针还提供了更安全的内存访问方式,避免了悬挂指针等问题。 在使用智能指针时,我们应该避免使用裸指针,尽量使用智能指针对象来管理动态分配的内存。另外,需要注意的是,智能指针的循环引用问题,如果存在循环引用,应该使用weak_ptr来打破引用环。 总之,智能指针C++中非常实用的特性,可以帮助我们更方便、安全地管理内存,提高程序的健壮性和可维护性。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

aspiretop

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值