unique_ptr:如何安全地共享原始指针

unique_ptr: How to safely share raw pointer

本文关键字:安全 共享 指针 原始 ptr 何安全 unique      更新时间:2023-10-16

我正在创建一个由unique_ptr管理的类,但由于各种原因,我需要为实现提供对该对象的原始指针的访问权限。但是,我希望确保用户不会无意中删除底层对象。我提出了以下示例代码:
(它是树结构的一部分,我需要能够查看树节点的成员,而无需实际分离它们。在这种情况下,shared_ptr似乎有些过头了。)

#include <memory>
using namespace std;
class unOnly
{
    ~unOnly() {}
public:
    unOnly() {}
    friend class default_delete<unOnly>;
};
int main()
{
    unique_ptr<unOnly> ptr(new unOnly());
}

这在gcc 4.4.5中为我编译。然而,我能确定在所有实现中,default_delete实际上是delete的对象,而不是一些私有的实现类吗?我应该写我自己的委托书来确定吗?

为什么不

class unOnly
{
    unOnly() {}
    ~unOnly() {}
    struct deleter { void operator()(unOnly* x) { delete x; }};
public:
    typedef std::unique_ptr<unOnly, deleter> handle;
    static handle create() { return handle(new unOnly); }
};
auto x = unOnly::create();

甚至

class unOnly
{
    ~unOnly() {}
    struct deleter { void operator()(unOnly* x) { delete x; }};
public:
    unOnly() {}
    typedef std::unique_ptr<unOnly, deleter> handle;
};
unOnly::handle x(new unOnly);

(我更喜欢前者,但后者可能更符合您的要求)

unique_ptr的要点(除了拥有一个拥有其指针的对象)是,您可以向它传递一个自定义的deleter,因此只写一个deleter而不做其他事情是有意义的,这似乎不必要地复杂。

引用标准:

20.7类模板unique_ptr

6。[…]

  template<class T, class D = default_delete<T>> class unique_ptr;

20.7.1.1.1

1类模板default_delete用作类模板unique_ptr的默认deleter(销毁策略)。

因此,似乎unique_ptr的实现需要使用default_delete作为默认的删除器。

编辑:
但这并不意味着你的方法是万无一失的,请参阅下面@RMartinhoFernandes的评论。