5、share_ptr使用赋值操作符可以从另外一个share_ptr或auto_ptr获得指针的管理权,其行为等同于构造函数,但它完全不能等同于一种拷贝,只是将原来的对象的引用技术加1,说白了是共享资源;而实际的指针赋值确是一种浅拷贝操作,关于深拷贝与浅拷贝可参与该篇文章:渐析java的浅拷贝和深拷贝。下面用代码范例来share_ptr的赋值和复制操作:(继续上面的例子)

 

#include
#include
using namespace std;
using namespace boost;

int main (int argc, const char * argv[])
{

    typedef vector< shared_ptr > sharedContainers;
    sharedContainers sharedArray(10);
    int i=0;
    for(sharedContainers::iterator pos = sharedArray.begin() ;pos!=sharedArray.end();++pos)
    {
        *pos = make_shared(++i);
    }
    cout<<"sharedArray[5]的初始值:"<<*sharedArray[5]<     cout<<"sharedArray[5]的初始引用计数为:"<     shared_ptr p1 = sharedArray[5];
    *p1 = 10;
    cout<<"sharedArray[5]经过赋值后的值:"<<*sharedArray[5]<     cout<<"sharedArray[5]赋值后的引用计数为:"<     shared_ptr p2(sharedArray[5]);
    cout<<"sharedArray[5]复制和赋值后的引用计数为:"<     cout<<"sharedArray[5]的地址:"<     *p2 = 5;
    cout<<"sharedArray[5]经过复制后的值:"<<*sharedArray[5]<     return 0;
   
}

  其输出结果为:

  sharedArray[5]的初始值:6
  sharedArray[5]的初始引用计数为:1
  sharedArray[5]经过赋值后的值:10
  sharedArray[5]赋值后的引用计数为:2
  sharedArray[5]复制和赋值后的引用计数为:3
  sharedArray[5]的地址:0x10010092c,p1的地址:0x10010092c,p2的地址:0x10010092c
  sharedArray[5]经过复制后的值:5

  可以看到,经过赋值和复制后的sharedArray[5],其引用计数增1。而且经过赋值和复制后的sharedArray[5]对象p1和p2所指向的地址完全相同。所以随便改变其中之一的值,另外两个对象指向的值也随之改变,这也是共享资源的精髓吧!

  6、share_ptr针对封装的指针要求,可以定制删除器,即使用构造函数shared_ptr(Y *p , D d)来构造shared_ptr指针。其中第一个参数是要被管理的指针,其含义与其他构造函数一样。而第二个参数,即删除器参数d则告诉shared_ptr在析构时不是使用普通的delete方法来析构指针p,而是用方法d来操作,即用d(p)来代替delete p。这里的d只需要能够像函数一样被调用,所以d既可以是一个函数对象,也可以是一个函数指针。这种删除器d比较适用于指针对象p在删除时有一定的要求,例如某中类指针,有专门的析构函数,但切记d的实参对象行为必须与delete一样,不能抛出异常,并且是可拷贝的。

  上面说了这么多,其实这只是shared_ptr的一小部分,还有很多涉及c++哲学方面的问题需要注意,例如延时释放、包装成员函数等。

  本文如有错误,欢迎指正,对此十分感谢!