[英]C++ dynamic_cast dowcast fails
我无法弄清楚为什么这个 dynamic_cast 会失败,即使 r 指向 MeshRenderer Object。
class MeshRenderer : public Component {...}
class Component : public GameObject {...}
class GameObject : protected TickEventConsumer, protected RenderEventConsumer, protected PhysicsTickEventConsumer {...}
class RenderEventConsumer 有一个虚方法,是 MeshRenderer 的基础。
class MeshRenderer: public Component {...} class Component: public GameObject {...} class GameObject: protected TickEventConsumer, protected RenderEventConsumer, protected PhysicsTickEventConsumer {...}
根据 Visual Studio,r 的 vftable 是正确的。
PS:这是我关于stackoverflow的第一个问题,如果我违反了任何准则或缺少相关信息,请告诉我。
编辑:虽然我现在知道答案,但为了清楚起见,我用一个独立的例子重现了这个错误:
#include <vector> #include <iostream> class RenderEventConsumer { virtual void onRender() {}; }; class RenderEventDispatcher { std::vector<RenderEventConsumer*> mConsumers; public: const std::vector<RenderEventConsumer*>& getConsumers() { return mConsumers; } void registerRenderEventConsumer(RenderEventConsumer* consumer) { mConsumers.push_back(consumer); } }; class GameObject: protected RenderEventConsumer {}; //changing this to public fixes dynamic_cast class Component: public GameObject {}; class MeshRenderer: public Component { public: void setup(RenderEventDispatcher& d) { d.registerRenderEventConsumer(this); } void onRender() override { } }; int main() { RenderEventDispatcher d; MeshRenderer* pt = new MeshRenderer(); pt->setup(d); for (RenderEventConsumer* r: d.getConsumers()) { MeshRenderer* m = dynamic_cast<MeshRenderer*>(r); if (m) { std::cout << "not nullptr\n"; } else { std::cout << "nullptr\n"; } } }
仅仅因为RenderEventConsumer
是一个基础MeshRenderer
,这并不意味着从RenderEventConsumer
派生的所有类也是(派生自) MeshRenderer
。
如果MeshRenderer
不是指向 object 的动态类型(的基础),则dynamic_cast
将返回 null。
这是如何发生的示例:
struct another_derived : RenderEventConsumer {} instance;
RenderEventConsumer* r = &instance;
// null, even through r is RenderEventConsumer*
dynamic_cast<MeshRenderer*>(r);
如果您发现需要使用dynamic_cast
,则意味着设计已损坏。 考虑使用例如访问者模式。
感谢 Kaldrr。
解决方案是从 RenderEventConsumer 公开派生。
class GameObject : public TickEventConsumer, public RenderEventConsumer, public PhysicsTickEventConsumer {...}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.