eXile 的专栏

说说C++智能指针(2): 标准库中的智能指针

  使用智能指针是C++中常用的管理内存的方式。关于智能指针的设计,各路C++高手也是各展神通。

  在1994年. Greg Colvin向C++标准委员会提出了自己设计的智能指针:auto_ptr和counted_ptr。auto_ptr实现基本的RAII管理,不可复制;counted_ptr采用引用计数实现了一个可复制的智能指针。两者用于不同的场合。
  但是标准委员会最终只通过了auto_ptr,并且对auto_ptr加入了一个古怪的“所有权转移”语义。后来auto_ptr和counted_ptr进入了Boost C++ 库,改名为scoped_ptr和shared_ptr。
  
  std::auto_ptr只所以设计为可拷贝的,也许是出于以下考虑,比如下例函数:

void f1(object* ptr);
object* f2();

   f1中的参数所指向的对象应该由谁来删除呢?调用者还是被调用者?如果不看程序文档的话,无法知道这一点。f2函数也存在同样的问题。

   用auto_ptr可以消除这种歧义性:

void f1(auto_ptr<object> ptr);
auto_ptr
<object> f2();

  
      尽管如此,auto_ptr的“所有权转移”语义还是会带来副作用,因为会修改原值的常量拷贝违背了一般的设计原则,它也许会在你意想不到的情况下就把对象转移了。它也不能用于标准容器中。
   所以auto_ptr在新的标准库已经不再推荐使用。取而代之的是unique_ptr。unique_ptr与auto_ptr类似,但限制了auto_ptr的拷贝行为。同时,像上面举的例子一样,unique_ptr可以作为函数的参数和返回值使用。这是因为C++增加了一个新的特征:右值引用。

   shared_ptr也进入了标准库。对于引用计数的智能指针而言,循环引用是一个大问题。标准库为此把shared_ptr定义为强引用指针,它还实现了一个弱引用指针weak_ptr。显然,标准库并没有从根本上解决循环引用的问题,它把这个问题交给了程序员。在一个简单的系统中,你可以区分使用shared_ptr和weak_ptr,以此来避免出现循环引用。但是在一个大的对象系统中,有时还是容易出错。循环引用的问题,严重减弱了shared_ptr的可用性。

   那么能不能自动检测是否出现循环引用呢?事实上,对于shared_ptr这种使用非侵入式策略实现的智能指针,是很难实现自动检测的。但是如果采用侵入式设计,我们可以引入一些接口,来解决这个问题。循环引用的检测,实际上是图论中的回路检测问题。

      本文由eXile 原创,转载请表明原贴地址。 http://www.cppblog.com/eXile/

posted on 2009-11-16 13:57 eXile 阅读(3686) 评论(1)  编辑 收藏 引用 所属分类: C/C++编程与设计STL/BOOST

评论

# re: 说说C++智能指针(2): 标准库中的智能指针 2009-11-17 13:07 QXE

什么叫循环引用?  回复  更多评论   


只有注册用户登录后才能发表评论。
网站导航: 博客园   IT新闻   BlogJava   知识库   博问   管理


导航

<2008年3月>
2425262728291
2345678
9101112131415
16171819202122
23242526272829
303112345

统计

常用链接

留言簿(18)

随笔分类

随笔档案

服务器编程

搜索

最新评论

阅读排行榜

评论排行榜