smart pointer
DESCRIPTION
之前分享的智能指针TRANSCRIPT
智能指针的使用和简单实现
Agenda什么是智能指针?
智能指针间的特性区别?
如何去设计智能指针?
什么是智能指针
何物:类的对象
方法:提供 -> 和 * 操作符来模拟一般指针的行为
好处:拥有权( Owenership )的管理
提供 -> 和 *template <typename T>class SmartPtr {public: explicit SmartPtr(T* pointee) {this->pointee_ = pointee;}; ~SmartPtr();
SmartPtr& operator =(const SmartPtr& other); T& operator *() const {return *pointee_;}; T* operator ->() const {return pointee_;};
private: T* pointee_;};
class Foo {public: void get();};
SmartPtr<Foo> foo(new Foo);foo->get();(*foo).get();
简单的例子 :Bad Codeint main(int argc, char** argv) {
string* my_name = new string("wuliang");
cout << *my_name << endl;
}
现实代码
string* my_name = new string("wuliang");
if ( 条件一 ){delete my_name; return;}
else if ( 条件 2) {delete my_name; return;}
delete my_name;
如果是智能指针
int main(int argc, char** argv) {
auto_ptr<string> my_name(newstring("wuliang"));
if ( 条件一 ){return;}
else if ( 条件 2) {return;}
}
智能指针提供的一般方法
get :得到具体的指针地址
* :间接引用对象
-> :间接引用对象的成员
= : auto_ptr 是 relese+copy , shared_ptr 只是 copy
release: 释放指针
reset: 释放指针并且设置新值
shared_ptr 还定义了其他一些
use_count 返回计数器值
swap 交换两个智能指针中的内容
目前常见的智能指针
std::auto_ptr
boost::shared_ptr 等
loki 中的 SmartPtr
它们之间的区别
std::auto_ptr 销毁式、不能应用于 STL容器和数组
scoped_ptr const std::auto_ptr
scoped_array const std::auto_ptr for array
shared_ptr 引用计数实现多个指针共享对象的所有权
shared_array
weak_ptr
intrusive_ptr ?
为什么需要 weak_ptr (强引用)
class Children {public:
boost::shared_ptr<Parent> his_parent;};boost::shared_ptr<Parent> father(new Parent());boost::shared_ptr<Children> son(new Children());
// memory leak will be happended in herefather->his_children = son;son->his_parent = father;
使用 weak_ptrclass Children {
public:
boost::weak_ptr<Parent> his_parent;
};
如何设计智能指针
Storage Policy
Ownership policy
Conversion policy
Checking policy
Storage Policy深层拷贝
引用计数
引用链接
摧毁式
深层拷贝
引用计数
引用计数
引用计数
引用链接
Conversion policy这段代码可以编译通过吗?
void Fun(Something* p);
...
SmartPtr<Something> sp(new Something);
Fun(something);
由设计者决定
template<typename T>
class SmartPtr {
public:
operator T* () {return pointee_};
};
Checking policy初始化检查:不应该接受 NULL ……
使用前检查:在调用 * 或者 -> 时,至少不应该返回
NULL ……
必要的错误报告
一切都组合起来
#include <cstdlib>#include <iostream>#include <string>
#include <loki/SmartPtr.h>
using namespace std;
typedef Loki::SmartPtr<string, Loki::RefCounted, Loki::DisallowConversion, Loki::AssertCheck, Loki::DefaultSPStorage> SmartPointer;
int main(int argc, char **argv) { SmartPointer myName(new string("Wu Liang")); SmartPointer copiedName = myName; cout << *myName << endl; cout << *copiedName << endl;}
参考资料
C++ 标准程序库的 4.2 章对 std::auto_ptr 的介绍
boost 文档中关于 shared_ptr 等的使用和 API 介绍
C++ 设计新思维的第 7 章中关于对智能指针实现的介绍
Q/A