共享指针和同一容器中的原始指针

时间:2013-04-26 15:00:27

标签: c++ pointers shared-ptr smart-pointers

我需要同时使用共享指针和原始指针填充容器。

如果使用no-op deleter和no-op(de)分配器构造,我猜shared_ptr<T>可能会被强制表现为T*

或者可能有通用智能指针,它绑定到不同的(智能和原始)指针类型?

或者shared_ptr可以指向一个对象,但管理相同类型的另一个(nullptr)对象的生命周期?

背景。我有简单的组件系统。有些组件是内置的,无需管理,原始指针就足够了。其他组件是外部DLL,它们必须在请求时附加,并在从“会话”中删除时分离。对于后者我使用包装器组件,它将在销毁时分离DLL。

编辑:后台更新。
EDIT2 :问题已更新。
EDIT3 :找到直接的解决方案。如果有兴趣,请看我的回答

3 个答案:

答案 0 :(得分:2)

一般来说,没有;容器只包含一种类型的对象。

您可以使用某种boost::variant<shared_ptr<T>, T*>对象作为包含的对象。但是你需要访问者访问它的元素。或者,您可以为boost::shared_ptr提供一个不会实际删除指向值的特殊删除对象。

答案 1 :(得分:2)

嗯,这实际上取决于您的需求,更具体地说,您希望在所有权方面实现的目标:

  1. 您的vector应该拥有shared_ptr<T>吗? (或者你可以存储指针?)
  2. 您的vector应该拥有T*吗?
  3. 然后有各种解决方案。

    1. 完全所有权:只需将T*封装在常规shared_ptr<T>
    2. 部分所有权:如上所述,您可以使用no-op删除器实例化shared_ptr<T>以包装T*
    3. 没有所有权:只使用shared_ptr<T>展开.get()并仅存储T*

答案 2 :(得分:1)

共享指针可能指向一个对象,但管理另一个对象的生命周期。奇怪的是,它可能无法管理,但仍指向某种东西。有一个特殊的构造函数,它接受另一个共享指针,用于确定要共享的对象。我们可以在其中传递空的共享指针。

template <typename T>
std::shared_ptr<T> fake_shared(T *ptr)
{
    std::shared_ptr<T> dummy (nullptr); // we have nothing to manage;
    std::shared_ptr<T> faked (dummy, ptr); // but we have something to point to;
    return faked;
}

此外,我们可以利用2个事实。首先,此构造函数将接受任何(其他)类型的共享指针。其次,std::shared_ptr<void>是合法的,可以用来更清楚地表达我们的意图。

template <typename T>
std::shared_ptr<T> fake_shared(T *ptr)
{
    std::shared_ptr<void> dummy (nullptr); // we have really nothing to manage;
    std::shared_ptr<T> faked (dummy, ptr); // but we have something to point to;
    return faked;
}

或者,可以使用构造函数,它接受自定义删除器,并将no-op删除器传递给它。

template <typename T>
std::shared_ptr<T> fake_shared(T *ptr)
{
    std::shared_ptr<T> faked (ptr, [](T *){}); // won't be deleted;
    return faked;
}

编辑:修订,共享无效,自定义删除。