- 个人主页:风间琉璃
- 版权: 本文由【风间琉璃】原创、在CSDN首发、需要转载请联系博主
- 如果文章对你有帮助、欢迎关注、点赞、收藏(一键三连)和订阅专栏哦
目录
一、智能指针定义
二、四种智能指针
1.std::auto_ptr
2.std::unique_ptr
4.std::weak_ptr
智能指针:将指针对象模板化实现了类型的通用,构成智能指针。
实现智能指针时需要考虑以下三个方面的问题:
①在对象构造时获取资源,在对象析构的时候释放资源,利用对象的生命周期来控制程序资源,即RAII特性。
②对
*
和->
运算符进行重载,使得该对象具有像指针一样的行为。③智能指针对象的拷贝问题。
RAII(Resource Acquisition Is Initialization)是一种利用对象生命周期来控制程序资源(如内存、文件句柄、互斥量等等)的简单技术。
智能指针就是要模拟原生指针的行为,当将一个指针赋值给另一个指针时,目的就是让这两个指针指向同一块内存空间,所以这里本就应该进行浅拷贝,但单纯的浅拷贝又会导致空间被多次释放,因此根据解决智能指针拷贝问题方式的不同,从而衍生出了不同版本的智能指针。
智能指针对象销毁时会自动释放记录的地址空间,很大程度上避免了内存泄漏的发生。
C++预定义了智能指针,可以直接使用,智能指针有4种,使用它们需要添加头文件memory。
智能指针的作用是管理一个指针,因为存在以下这种情况:申请的空间在函数结束时忘记释放,造成内存泄漏。所以智能指针的作用原理就是在函数结束时自动释放内存空间,不需要手动释放内存空间。
操作的方法:在构造函数时,将类外需要管理的指针传进去,可以给个空的缺省值,然后重载“->”“*”“=”…等符号,然后在析构函数时,释放这个指针空间,形成对这个指针的智能的管理。
auto_ptr是c++98版本库中提供的智能指针,该指针解决上诉的问题采取的措施是管理权转移的思想,也就是原对象拷贝给新对象的时候,原对象就会被设置为nullptr,此时只有新对象指向一块资源空间。
auto_ptr是C++98中引入的智能指针,auto_ptr通过管理权转移的方式解决智能指针的拷贝问题,保证一个资源在任何时刻都只有一个对象在对其进行管理,这时同一个资源就不会被多次释放了
如果auto_ptr调用拷贝构造函数或者赋值重载函数后,如果再去使用原来的对象的话,那么整个程序就会崩溃掉(因为原来的对象被设置为nullptr),这对程序是有很大的伤害的。所以C++17移除了用auto_ptr智能指针。
class Object{
public:
Object(string s=""):str(s){}
~Object(){cout<<"~Object()"<str<str = s;
}
private:
string str;
};
int main()
{
//管理 string *的指针
auto_ptr pa(new string("hello"));
cout<c_str()< pa1 = pa;//pa将被置空
//cout<c_str()<c_str()< ao(new Object("hello"));
auto_ptr
unique_ptr是C++11中引入的智能指针,unique_ptr通过防拷贝的方式解决智能指针的拷贝问题,它直接将拷贝构造函数和赋值重载函数给禁用掉,也就是简单粗暴的防止对智能指针对象进行拷贝,这样也能保证资源不会被多次释放。
unique_ptr对其持有的堆内存具有唯一拥有权,也就是不可以拷贝或者复制给其他对象,当unique_ptr对象销毁时会释放掉其持有的堆内存。
int main()
{
std::unique_ptr up1(new int(0));
//std::unique_ptr up2(up1); //error
return 0;
}
share_ptr是c++11版本库中的智能指针,shared_ptr允许多个智能指针可以指向同一块资源,并且能够保证共享的资源只会被释放一次,因此是程序不会崩溃掉。
shared_ptr采用的是引用计数原理来实现多个shared_ptr对象之间共享资源:
①shared_ptr在内部会维护着一份引用计数,用来记录该份资源被几个对象共享。
②当一个shared_ptr对象被销毁时(调用析构函数),析构函数内就会将该计数减1。
③如果引用计数减为0后,则表示自己是最后一个使用该资源的shared_ptr对象,必须释放资源。
④如果引用计数不是0,就说明自己还有其他对象在使用,则不能释放该资源,否则其他对象就成为野指针。
引用计数是用来记录资源对象中有多少个指针指向该资源对象。
销毁过程:
class Object{
public:
Object(string s=""):str(s){}
~Object(){cout<<"~Object()"<str<str = s;
}
private:
string str;
};
int main()
{
shared_ptr ss(new string("byebye"));
cout<c_str()< ss1 = ss;//共享
ss1->append("冬天");
cout<c_str()<c_str()< so(new Object("byebye"));
shared_ptr
weak_ptr是C++11中引入的智能指针,weak_ptr不是用来管理资源的释放的,它主要是用来解决shared_ptr的循环引用问题的。
weak_ptr支持用shared_ptr对象来构造weak_ptr对象,构造出来的weak_ptr对象与shared_ptr对象管理同一个资源,但不会增加这块资源对应的引用计数。
weak_ptr基本上很少使用,这里不做详细介绍。
C++11和boost中智能指针的关系:
①C++98中产生了第一个智能指针auto_ptr。
②C++boost给出了更实用的scoped_ptr、shared_ptr和weak_ptr。
③C++TR1,引入了boost中的shared_ptr等。不过注意的是TR1并不是标准版。
④C++11,引入了boost中的unique_ptr、shared_ptr和weak_ptr。注意,unique_ptr对应的就是boost中的scoped_ptr,并且这些智能指针的实现原理是参考boost中实现的。
boost库是为C++语言标准库提供扩展的一些C++程序库的总称,boost库社区建立的初衷之一就是为C++的标准化工作提供可供参考的实现,比如在送审C++标准库TR1中,就有十个boost库成为标准库的候选方案。