C++文档阅读笔记-Smart Pointers in C++ and How to Use Them
Posted IT1995
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了C++文档阅读笔记-Smart Pointers in C++ and How to Use Them相关的知识,希望对你有一定的参考价值。
此篇博文,介绍了C++中智能指针,为何要使用智能指针,以及如何去用。
指针可使得程序直接访问堆区内存。通过指针,可以直接对原始资源进行修改,也就是说指针指向的就是一手资源。
Problems with Normal Pointers
如下代码:
#include <iostream>
using namespace std;
class Rectangle
private:
int length;
int breadth;
;
void fun()
// By taking a pointer p and
// dynamically creating object
// of class rectangle
Rectangle* p = new Rectangle();
int main()
// Infinite Loop
while (1)
fun();
上面代码的fun()函数中,创建了Rectangle对象,Rectangle对象包含2个int型成员,分别表示长和宽。当这个函数结束后,指针p并没有被销毁,原因是没有调用delete p,这就造成堆区内存浪费。C++程序有个主旨就是“我们不需变量,我们需要内存”。
在main()函数中,fun()函数被无止境的调用,这也就造成了,无止境的创建p,但不去释放p的资源,导致这块内存程序员无法使用,这就叫内存泄漏。C++11为了解决这一问题,提出了智能指针。
Introduction of Smart Pointers
每一个C++程序员都会不自觉的犯一种错,那就是创建的指针,忘记手动释放,最后导致程序崩溃。像Java、C#都有自己的垃圾回收机制,去回收不用了的堆区内存,避免出现内存泄漏的问题。C++11也推出了自己的一套机制,那就是智能指针。如果程序员想销毁一个对象时,不需要再调用delete方法了,智能指针会自动将其销毁。
其实智能指针就是一个被封装了的类,封装了一些操作符,如*、->。操作智能指针就和普通指针一样。唯一的区别就是普通指针需要自己手动回收资源。
当智能指针在指定的生命周期结束后,会自动释放内存。
智能指针的封装,可以参考如下代码:
#include <iostream>
using namespace std;
class SmartPtr
int* ptr; // Actual pointer
public:
// Constructor: Refer https:// www.geeksforgeeks.org/g-fact-93/
// for use of explicit keyword
explicit SmartPtr(int* p = NULL) ptr = p;
// Destructor
~SmartPtr() delete (ptr);
// Overloading dereferencing operator
int& operator*() return *ptr;
;
int main()
SmartPtr ptr(new int());
*ptr = 20;
cout << *ptr;
// We don't need to call delete ptr: when the object
// ptr goes out of scope, the destructor for it is automatically
// called and destructor does delete ptr.
return 0;
输出为:
20
上面的代码仅仅适用于int类型,如果需要创建任意类型的对象,就需要使用Template,模板编程如下代码:
#include <iostream>
using namespace std;
// A generic smart pointer class
template <class T>
class SmartPtr
T* ptr; // Actual pointer
public:
// Constructor
explicit SmartPtr(T* p = NULL) ptr = p;
// Destructor
~SmartPtr() delete (ptr);
// Overloading dereferencing operator
T& operator*() return *ptr;
// Overloading arrow operator so that
// members of T can be accessed
// like a pointer (useful if T represents
// a class or struct or union type)
T* operator->() return ptr;
;
int main()
SmartPtr<int> ptr(new int());
*ptr = 20;
cout << *ptr;
return 0;
输出如下:
20
注意:智能指针一般用于管理资源,比如handles和Sockets,如文件句柄、TCP套接字。
Types of Smart Pointers
1.unique_ptr
unique_ptr存储了单独的一个指针。可以把当前智能指针的对象移除,添加新的对象。如下图所示,unique_pointer P1指向了一个object,只有将P1中的object移除后P2才能指向object。
代码如下:
#include <iostream>
using namespace std;
#include <memory>
class Rectangle
int length;
int breadth;
public:
Rectangle(int l, int b)
length = l;
breadth = b;
int area()
return length * breadth;
;
int main()
unique_ptr<Rectangle> P1(new Rectangle(10, 5));
cout << P1->area() << endl; // This'll print 50
// unique_ptr<Rectangle> P2(P1);
unique_ptr<Rectangle> P2;
P2 = move(P1);
// This'll print 50
cout << P2->area() << endl;
// cout<<P1->area()<<endl;
return 0;
输出:
50
50
2.shared_ptr
多个shared_ptr可以在同一时间指向1个object,并且提供了计数功能,记录这个对象被多少个shared_ptr指向。调用的方法是use_count()。
代码如下:
#include <iostream>
using namespace std;
#include <memory>
class Rectangle
int length;
int breadth;
public:
Rectangle(int l, int b)
length = l;
breadth = b;
int area()
return length * breadth;
;
int main()
shared_ptr<Rectangle> P1(new Rectangle(10, 5));
// This'll print 50
cout << P1->area() << endl;
shared_ptr<Rectangle> P2;
P2 = P1;
// This'll print 50
cout << P2->area() << endl;
// This'll now not give an error,
cout << P1->area() << endl;
// This'll also print 50 now
// This'll print 2 as Reference Counter is 2
cout << P1.use_count() << endl;
return 0;
输出:
50
50
50
2
3.weak_ptr
这个weak_ptr就是shared_ptr的简化版,就是删除了其指向计数的功能。
C++提供的智能指针有4个分别是:auto_ptr、unique_ptr、shared_ptr、weak_ptr
估计是auto_ptr太简单了,所以才没有相关介绍。
以上是关于C++文档阅读笔记-Smart Pointers in C++ and How to Use Them的主要内容,如果未能解决你的问题,请参考以下文章
C++文档阅读笔记-Smart Pointers in C++ and How to Use Them
std::vector of objects / pointers / smart pointers to pass objects(总线错误:10)?
Move语义和Smart Pointers先导(以一个例子说明)
C++文档阅读笔记-Understanding nullptr in C++