简单的C++智能指针

来源:互联网 发布:疯狂的美工京东 编辑:程序博客网 时间:2024/06/06 05:47

本文链接:简单的C++智能指针

­

从书上看到了一个C++智能指针的例子,感觉不错,小改进了下,放出来。

 

智能指针的大意是:对普通的类(假设C)指针进行包装,内部维护一个引用计数。程序中只要使用智能指针包装类(假设SafeC)就行了。用的时候只用new C(), 然后把其给包装类进行构造,然后就随便用啦,不用担心C的析构问题了。

 

众所周知,C++中如果需要动态申请内存的话,就一定要释放。可是不是所有new出来的对象都能明确的知道该在哪里释放。释放的话,不知道在哪里释放才好,总不能某处正在使用着呢,就给delete了;不释放的话,就是传说中的内存泄漏。

所以,智能指针(好像也有叫安全指针的)的作用就显出来了。把一个申请来的对象指针,扔给智能指针去管理。智能指针会在对其所有引用都释放后,把内部管理的指针所指向的对象删除。使用起来的效果就像.Net和Java的引用一样。不过垃圾回收的机理应该和这个有些不同。

 

智能指针只使用值传递就可以,没有必要使用指针传递或引用传递,虽然效率高一点点。需要注意的是,智能指针就不要去new了,不然就失去其本来的意义了。

 

代码我改动了不少,还添加了测试代码。书上的代码只有很简单的非泛型的SafeC类。各种优缺点大家自己体会吧。(和Java或者是.Net对比一下,发现了这样写的优点了吧~)

另外说明一点:这个代码是没法在普通的C++环境下编译的,因为用的是C++.Net……用的.Net的控制台输出。大家把所有的输出代码删掉或改用C++的输出流就可以运行了(不要告诉我你看不出来哪个是.Net的东西啊……)。

 

另外:这个安全指针不是线程安全的,多线程中跨线程使用会出问题,需要添加线程锁。加锁一种可能的做法是:再维护一个锁对象的指针,在所有能接收到C新实例的指针的构造器中进行初始化,并与C的指针一同析构,在所有可能改变引用计数的地方进行线程同步,如构造器,赋值操作符,析构器。

 

代码:(自己写主函数)

相关测试代码:

输出:

­In Singleton's Constructor.
>>>>> object in stack test:
! in C1.C1, id: 1
reference count in SafeC.constructor: 1
s1
reference count in SafeC.constructor: 2
s2
rs3
reference count in SafeC.constructor: 3
invoke: s4->Func()
! in C1.f, id: 1
<<<<< end stack test.
>>>>> object in heap test:
ps5
! in C1.C1, id: 2
reference count in SafeC.constructor: 1
rs6
! in C1.C1, id: 3
reference count in SafeC.constructor: 1
s7
reference count in SafeC.constructor: 2
delete ps5
in SafeC.destructor, before excute, count: 2
 and the instance's id: 2
<<<<< end heap test.
>>>>> method return value test:
! in C1.C1, id: 10
reference count in SafeC.constructor: 1
<<<<< end method return value test.
in SafeC.destructor, before excute, count: 1
 and the instance's id: 10
 and delete the pointer to instance !! instance's id: 10
! in C1.~C1, id: 10
in SafeC.destructor, before excute, count: 1
 and the instance's id: 2
 and delete the pointer to instance !! instance's id: 2
! in C2.~C2, id: 2
! in C1.~C1, id: 2
in SafeC.destructor, before excute, count: 3
 and the instance's id: 1
in SafeC.destructor, before excute, count: 2
 and the instance's id: 1
in SafeC.destructor, before excute, count: 1
 and the instance's id: 1
 and delete the pointer to instance !! instance's id: 1
! in C1.~C1, id: 1

原创粉丝点击