智能指针:或谁拥有你的宝贝?

C ++全是关于内存所有权的
又名“ 所有权语义

一块动态分配的内存的所有者负责释放该内存。 所以这个问题真的变成谁拥有记忆。

在C ++中,所有权由一个RAW指针包装在内部的类型记录,因此在一个好的(IMO)C ++程序中,很少见到RAW RAW指针传递过来(因为RAW指针没有推断的所有权,所以我们不能告诉谁拥有记忆,因此如果没有仔细阅读文件,你不能分辨谁对所有权负责)。

相反,很少见到存储在类中的RAW指针,每个RAW指针都存储在它自己的SMART指针包装器中。 (注意:如果你不拥有一个对象,你不应该存储它,因为你不知道它何时会超出范围并被销毁。)

所以问题是:

  • 人们会遇到什么类型的所有权语义?
  • 用什么标准类来实现这些语义?
  • 你觉得他们有什么用处?
  • 让我们为每个答案保留一种语义所有权,以便他们可以单独进行投票

    概要:

    概念智能指针很简单,而且天真的实现很容易。 我见过很多尝试的实现,但总是以某种方式破坏了它,这对于偶然使用和示例并不明显。 因此,我建议您始终使用库中经过良好测试的“智能指针”,而不是滚动自己的。 std :: auto_ptr或其中一个boost智能指针似乎涵盖了我所有的需求。

    的std :: auto_ptr的<T>:

    一个人拥有这个物体。
    但允许转让所有权。

    用法:
    ======
    这使您可以定义显示所有权显式转移的接口。

    升压:: scoped_ptr的<T>

    一个人拥有这个物体。
    不允许转让所有权。

    用法:
    ======
    用于显示明确的所有权。
    对象将被析构函数销毁或者在显式重置时销毁。

    boost :: shared_ptr <T>(std :: tr1 :: shared_ptr <T>)

    多重所有权。
    这是一个简单的引用计数指针。 当引用计数达到零时,对象被销毁。

    用法:
    ======
    当对象可以拥有多个在编译时无法确定生命周期的owers时。

    升压::的weak_ptr <T>

    与shared_ptr <T>一起使用。
    在可能发生指针循环的情况下。

    用法:
    ======
    当只有循环维持一个共享的refcount时,用于停止保留对象的循环。


    对我来说,这三种类型涵盖了我的大部分需求:

    shared_ptr - 引用计数,当计数器达到零时解除分配

    weak_ptr - 与上面相同,但是它是shared_ptr的“奴隶”,不能释放

    auto_ptr - 当创建和取消分配发生在同一个函数内部时,或者当对象必须被视为一个所有者时。 当您将一个指针指定给另一个指针时,第二个从第一个'抢夺'对象。

    我有我自己的这些实现,但它们也可以在Boost

    我仍然通过引用传递对象( const只要有可能),在这种情况下,被调用的方法必须假定该对象仅在调用期间处于活动状态。

    还有一种我使用的指针,我称之为hub_ptr 。 这是当你有一个对象必须可以嵌入它的对象(通常作为一个虚拟的基类)。 这可以通过将weak_ptr传递给它们来解决,但是它本身没有shared_ptr 。 因为它知道这些对象的寿命不会超过他,所以它将一个hub_ptr传递给它们(它只是一个模板封装到一个常规指针)。


    简单的C ++模型

    在我看到的大多数模块中,默认情况下,假设接收指针获得所有权。 事实上,放弃指针所有权的函数/方法都非常罕见,并且在其文档中明确地表达了这一事实。

    该模型假设用户只是他/她明确分配的所有者 。 其他一切都会自动处理(在范围退出或通过RAII)。 这是一个类似C的模型,由于大多数指针由拥有对象所拥有的事实所扩展,这些对象将自动或在需要时释放它们(主要是在所述对象被破坏的情况下),并且对象的生存期是可预测的(RAII是你的朋友,再次)。

    在这个模型中,原始指针是自由流通的,而且大多不是危险的(但是如果开发人员足够聪明,他/她将尽可能使用引用)。

  • 生指针
  • 性病:: auto_ptr的
  • 提高:: scoped_ptr的
  • 智能指向C ++模型

    在充满智能指针的代码中,用户可能希望忽略对象的生命周期。 所有者永远不会是用户代码:它是智能指针本身(又是RAII)。 问题是循环引用与引用计数智能指针混合在一起可能是致命的 ,因此您必须同时处理共享指针和弱指针。 所以你仍然有所有权考虑(弱指针可能指向没有,即使它比原始指针的优势是它可以告诉你这样做)。

  • 提高:: shared_ptr的
  • 提高:: weak_ptr的
  • 结论

    无论我描述的模型是什么, 除非例外,接收指针都没有收到它的所有权知道谁拥有谁是非常重要的 。 即使对于大量使用引用和/或智能指针的C ++代码。


    没有共享所有权。 如果你这样做,确保只有你不能控制的代码。

    这解决了100%的问题,因为它会迫使你理解每件事物如何相互作用。

    链接地址: http://www.djcxy.com/p/20767.html

    上一篇: Smart Pointers: Or who owns you baby?

    下一篇: How to achieve smooth UI updates every 16 ms?