追踪shared_ptr的所有者?

时间:2016-07-24 15:34:58

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

在我们的应用程序中,我们即将(最终......)从原始指针切换到使用C ++ 11 smart_ptr模板。

我们的应用程序中偶尔会出现一些错误,其中(非C ++)对象在访问then-dealloc< d>对象时,仍然会导致过去导致崩溃的C ++对象的引用。

不确定这是否是一个愚蠢的问题 - 但有没有办法利用smart_ptr对象和' 转储'当没有人希望不再持有对C ++对象的引用时,这些对象仍然保留在C ++对象上?

我想我要求的是在某个时间点列出smart_ptr<MyClass> 的所有所有者的方式。

任何建议都非常感谢!

3 个答案:

答案 0 :(得分:1)

不要相信这对于任何开箱即用的c ++智能指针都是可行的。您可以通过简单地包装shared_ptr来实现相同的效果。

template<typename T>
class mySmartPtr : boost::noncopyable{
    public:
         // This method should be the only way this object can be copied
         // as the copy constructors are made private
         // The newOwnerName parameter can be used to populate m_onwers.
         static mySmartPtr<T> newOwner(mySmartPtr<T>&, std::string newOnwerName); 
    private:
         std::shared_ptr<T> m_ptr;
         static std::vector<std::string> m_owners;
};

答案 1 :(得分:1)

没有。如果没有创建自己的智能指针类来包装std::unique_ptrstd::shared_ptr(忽略已弃用的std::auto_ptr)来跟踪此信息,则无法执行此操作。 标准类本身不会跟踪这些信息(成本太高)。

另一种方法是修改标准库实现的代码以跟踪该信息。由于您可以继续使用标准名称,因此 代码的侵入性较小。但可能比包装类和使用包装器更棘手。

答案 2 :(得分:0)

  

我们的应用程序中偶尔会出现一些错误,其中(非C ++)对象在访问then-dealloc'd对象时仍然会引起对C ++对象的引用,从而导致崩溃。

这是严肃的,不容忽视。

如果您在对象上提供第三方库组件观察者状态,那么第三方组件的观察者必须不会超过您的对象。

此问题有3个常见原因:

  1. 第三方组件的生命周期管理不当(您在关闭第三方观察者之前删除了被观察对象)

  2. 未正确检测到穿越案件(导致上述1)

  3. 如果你是组件,你必须从第三方框架接受关于何时处理你的对象的命令。

  4. 在涉及shared_ptr之前,您应首先证明shared_ptr可能合法地销毁该对象。如果第三方组件具有“注销”方法,则可以通过以下方式解决此问题:

    1. 确保第三方组件和被观察对象的所有权由相同的shared_ptr或
    2. 控制
    3. 在shared_ptr上使用自定义删除器,以便在最终删除第三方对象上的受控对象之前取消注册。
    4. 如果这一切都不清楚,那么就该好好长时间看看对象的生命周期了。绘制序列图通常会有所帮助。