2015-12-04 126 views
2

我有一个类层次结构,我想从中共享并将其转换为特定的类类型。所以,我想这一点:如何识别类类型以将shared_ptr转换为该类型

class A : public std::enable_shared_from_this 
{ 
    std::shared_ptr<A> getSharedFromThis() 
    { 
     return std::static_pointer_cast<A>(shared_from_this()); 
    } 
}; 

class B : public A 
{ 
    std::shared_ptr<B> getSharedFromThis() 
    { 
     return std::static_pointer_cast<B>(shared_from_this()); 
    } 
}; 

在超我可以写一个模板变量,但它仍然是不冷静:

template <typename T> 
std::shared_ptr<T> getSharedFromThis() 
{ 
    return std::static_pointer_cast<T>(shared_from_this()); 
} 

我怎样才能使通用的,因此,它会明白,这是在课堂上B并将其转换为Bshared_ptr,现在在同一层次结构中的100个类中编写相同的逻辑。

+1

正在使用CRTP合理的解决方案吗? – TartanLlama

+0

@TartanLlama与CRTP我将继承所有层次结构中的同一个类。 – Narek

+0

顺便说一句,如果你想使用'std :: shared_from_this',那么你必须从'std :: enable_shared_from_this'派生你的类。 – Nawaz

回答

1

看来你的关键问题是推导出这个叫做模板getSharedFromThis()的类型。由于成员函数是在基类中实现的,因此它没有任何派生类的调用 - 除非以某种方式指定。使用非成员函数调用基函数将利用这一整齐护理:

template <typename T> 
auto getSharedFromThis(T& object) -> decltype(object.template getSharedFromThis<T>()) { 
    return object.template getSharedFromThis<T>()); 
} 

这样就没有必要写任何东西任何派生类的拿到getSharedFromThis()功能得到适当类型std::shared_ptr<T>。作为奖励,具有暴露getSharedFromThis()函数的基础的类似层次结构可以使用相同的函数。您可能希望使用指针类型重载该函数,因此您可以在成员函数中使用getSharedFromThis(this)而不是getSharedFromThis(*this)

+0

我不明白你的解决方案。你在模板函数的主体中调用了什么'getSharedFromThis'。请解释一下你的代码。 – Narek

+0

@Narek:这个想法是有一个基类函数模板'getSharedFromThis()',它实际上就是你写的成员(标记为“不酷”)并且使用非成员函数模板中的这个成员。我的非成员函数的实现只是调用基本成员(这里唯一古怪的事情是奇怪的'template'关键字,因为'getSharedFromThis'是一个独立的名字,所以需要这个关键字。 –

2

您正在查看covariant return type明智smart pointers。这将是一个不错的功能,但你不能这样做。唯一可行的方法是在shared_ptr<A>shared_ptr<B>之间建立等级关系,在不久的将来情况将不会如此。

您必须坚持使用父类模板或使用能够实现协变返回类型范例的包装器对象(这意味着仔细的声明和由于副本造成的可能的错误)。

std::enable_shared_from_this在您的示例中未正确使用,因为它是模板类。

如果getter放置在父类中,请小心使用dynamic_pointer_cast

相关问题