如何使用shared_ptr创建克隆方法并从enable_shared_from_this继承

时间:2010-09-07 02:35:17

标签: c++ shared-ptr

我已经看到编写一个返回boost :: shared_ptr的克隆方法的有用方法是

class A
{
public:
  shared_ptr<A> Clone() const
  {
    return(shared_ptr<A>(CloneImpl()));
  }
protected:
  virtual A* CloneImpl() const
  {
    return(new A(*this));
  }
};

class B : public A
{
public:
  shared_ptr<B> Clone() const
  {
    return(shared_ptr<B>(CloneImpl()));
  }
protected:
  virtual B* CloneImpl() const
  {
    return(new B(*this));
  }
};

这允许使用与常规指针的协方差,同时仍将其包装在智能指针的安全性中。我的问题是我的类B需要从boost :: enable_shared_from_this继承,因为在构造之后它需要用一个单独的类注册自己,将共享指针传递给它自己。我有一个Create方法,它包装构造和注册,以确保它们总是一起出现。但是,上述克隆方法实现无法处理此要求。注册不能在CloneImpl中发生,因为没有shared_ptr存在“拥有”该对象,阻止调用shared_from_this(),如果该逻辑不在虚函数中,则指向B的shared_ptr不知道B的注册需求什么时候克隆处理这个问题的最佳方法是什么?

1 个答案:

答案 0 :(得分:7)

由于您已经通过非虚拟Clone()函数自行实现了 public 接口协方差,因此您可以考虑放弃CloneImpl()函数的协方差。

如果您只需要shared_ptr而不需要原始指针,那么您可以这样做:

class X
{
public:
  shared_ptr<X> Clone() const
  {
    return CloneImpl();
  }
private:
  virtual shared_ptr<X> CloneImpl() const
  {
    return(shared_ptr<X>(new X(*this)));
  }
};

class Y : public X
{
public:
  shared_ptr<Y> Clone() const
  {
    return(static_pointer_cast<Y, X>(CloneImpl())); // no need for dynamic_pointer_cast
  }
private:
  virtual shared_ptr<X> CloneImpl() const
  {
    return shared_ptr<Y>(new Y(*this));
  }
};

CloneImpl()将始终返回shared_ptr<Base>,现在您可以在B::CloneImpl()函数中注册对象并返回已注册的shared_ptr。