我正在为我的一个项目构建一个简单的游戏设计.我有以下课程:
class Character
{
public:
virtual void Display();
virtual void SetParameters( char* param, ... );
};
class NonPlayableCharacter : public Character
{
public:
virtual void Display();
virtual void SetParameters( char* paaram, ... );
int GetNPCState();
}
Run Code Online (Sandbox Code Playgroud)
然后我有一堆派生自Character或NonPlayableCharacter的类.我这样定义它:
std::vector<Character*> _allChar;
Run Code Online (Sandbox Code Playgroud)
我的问题是,在任何给定的时间我都想对矢量的一个元素执行一些操作.因此,从向量中获取元素我无法直接调用该方法,GetNPCState()因为向量中的元素是Character*类型.这样做:
_allChar[0]->GetNPCState();
Run Code Online (Sandbox Code Playgroud)
不起作用.所以我尝试用着名的dynamic_cast来做:
NonPlayableCharacter* test = dynamic_cast<NonPlayableCharacter*>(_allChar[0]);
test->GetNPCState();
Run Code Online (Sandbox Code Playgroud)
最后一次尝试的问题是GetNPCState()崩溃,因为对象是null,我知道(通过调试)_allChar [0]不为空.
C++(4)中有几种类型的强制转换,其中2个是有兴趣的:
static_cast 假设你知道自己在做什么dynamic_cast 在运行时检查你"猜对"的权利注意:简化,dynamic_cast也允许包含虚拟基础的交叉投射和强制转换.
dynamic_cast实际上有3个版本,具体取决于目标的性质:
dynamic_cast<T&>(u)),那么如果检查失败则dynamic_cast抛出std::bad_cast异常dynamic_cast<T*>(p)),那么如果检查失败则dynamic_cast返回空指针void*,则dynamic_cast返回完整对象的地址在这种情况下,您可以:
dynamic_cast<NonPlayableCharacter*>(_allChar[0])->getNPCState()到
dynamic_cast<NonPlayableCharacter&>(*_allChar[0]).getNPCState(),并让异常传播NonPlayableCharacter* test这里)的结果是否为非null后
NonPlayableCharacter* test = dynamic_cast<NonPlayableCharacter*>(_allChar[0]);
Run Code Online (Sandbox Code Playgroud)
你应该检查是否test是NULL.即使_allChar[0]不是NULL,如果它指向的对象不是a ,dynamic_cast也可以返回.NULLNonPlayableCharacter
所以正确的版本是:
NonPlayableCharacter* test = dynamic_cast<NonPlayableCharacter*>(_allChar[0]);
if (test)
{
test->GetNPCState();
}
Run Code Online (Sandbox Code Playgroud)