【发布时间】:2018-11-12 17:36:37
【问题描述】:
考虑以下使用奇怪重复模板模式 (CRTP) 的类:
template <typename T>
class Base
{
public:
virtual ~Base() {}
void typeOfThis()
{
cout << "Type of this: " << typeid(this).name() << '\n';
cout << "Type of *this: " << typeid(*this).name() << '\n';
}
void callFuncOfTemplateParam()
{
static_cast<T*>(this)->hello();
}
};
class Derived : public Base<Derived>
{
public:
void hello()
{
cout << "Hello from Derived!" << '\n';
}
};
当我执行以下操作时:
Base<Derived> * basePtrToDerived = new Derived();
basePtrToDerived->typeOfThis();
basePtrToDerived->callFuncOfTemplateParam();
我得到了这些对我有意义的结果:
Type of this: P4BaseI7DerivedE
Type of *this: 7Derived
Hello from Derived!
显然,在callFuncOfTemplateParam 内部对hello 的调用成功,因为this 指针指向Derived 的一个实例,这就是我能够从@987654329 类型转换this 指针的原因@ 类型为Derived*。
现在,我的困惑出现了,因为当我执行以下操作时:
Base<Derived> * basePtrToBase = new Base<Derived>();
basePtrToBase->typeOfThis();
basePtrToBase->callFuncOfTemplateParam();
我得到以下结果:
Type of this: P4BaseI7DerivedE
Type of *this: 4BaseI7DerivedE
Hello from Derived!
this 和 *this 的类型是有道理的,但我不明白对 hello 的调用如何成功。 this 不指向Derived 的实例,那为什么我可以将this 的类型从Base<Derived> 转换为Derived?
请注意,我还将对static_cast<T*>(this)->hello(); 的调用替换为对dynamic_cast<T*>(this)->hello(); 的调用,我仍然获得相同的结果。我预计 dynamic_cast 会返回 nullptr,但它没有。
我对这些结果感到非常惊讶。感谢您帮助澄清我的疑问!
【问题讨论】:
标签: c++ crtp dynamic-cast static-cast