三种指针
- 空指针:值为null的指针
- 空悬指针:指向已经销毁的对象或者已经回收的地址的指针
- 野指针:未经初始化的指针
1. 原始指针的问题
指向对象的原始指针如果时坏的,尤其时当暴露给其他线程时,容易发生内存方面的问题;比如总容易放生的空悬指针问题。
例:
有俩个指针p1,p2,指向堆上的同一个对象object,p1,p2位于不同的线程中,假设线程A通过p1将对象销毁了(尽管把p1置为了NULL),那p2就成了空悬指针,这是一种典型的C++内存错误。
2.一个"解决办法"
一个解决空悬指针的办法是,引入一层间接层,让p1和p2所指的对象永久有效。比如proxy对象,这个对象,持有一个指向object的指针。(从C语言的角度,p1,p2都是二指针)
当销毁object之后,proxy对象继续存在,其值变为0.而p2也没有变为空悬指针,它可以通过查询proxy的内容来判断Object是否还活着。
要线程安全是释放Object也不是那么容易,race condition依旧存在,比如p2看第一眼的时候proxy不是零,正准备去调用object,期间对象已经被p1给销毁了。
3.一个更好的解决方法
为了安全地释放proxy,我们可以引入引用技计数(reference counting),再把p1和p2都从指针变成对象sp1和sp2。proxy现在有两个成员,指针和计数器。
一开始,有两个引用,计数值为2
sp1析构了,引用计数的值减为1
sp2也析构了,引用计数降为0,可以安全的销毁proxy和object