有没有比使用dynamic_cast更快的方法在运行时检测对象类型?

sha*_*oth 6 c++ polymorphism dynamic visual-c++

我有一个类型的层次结构--GenericClass和一些派生类,包括InterestingDerivedClass,GenericClass是多态的.有一个界面

interface ICallback {
    virtual void DoStuff( GenericClass* ) = 0;
};
Run Code Online (Sandbox Code Playgroud)

我需要实现.然后我想检测传递给ICallback :: DoStuff()的GenericClass*指针实际上是指向InterestingDerivedClass的指针的情况:

class CallbackImpl : public ICallback {
    void DoStuff( GenericClass* param ) {
        if( dynamic_cast<InterestingDerivedClass*>( param ) != 0 ) {
            return; //nothing to do here
        }
        //do generic stuff
    }
}
Run Code Online (Sandbox Code Playgroud)

GenericClass和派生类是我无法控制的,我只控制CallbackImpl.

我对dynamic_cast语句进行了定时 - 它需要大约1400个周期才能接受,但看起来不是很快.我试着在调试器中读取dynamic_cast期间执行的内容的反汇编,看到它需要很多指令.

因为我真的不需要指向派生类的指针,是否有更快的方法在运行时使用RTTI检测对象类型?也许某些特定于实现的方法只检查"是一个"关系但不检索指针?

180*_*ION 12

我总是把它dynamic_cast作为代码气味使用.您可以在所有情况下使用多态行为替换它并提高代码质量.在你的例子中,我会做这样的事情:

class GenericClass
{
  virtual void DoStuff()
  {
    // do interesting stuff here
  }
};

class InterestingDerivedClass : public GenericClass
{
  void DoStuff()
  {
    // do nothing
  }
};

class CallbackImpl : public ICallback {
    void DoStuff( GenericClass* param ) {
        param->DoStuff();
    }
}
Run Code Online (Sandbox Code Playgroud)

在您的情况下,您无法修改目标类,您正在编程为GenericClass类型声明所暗示的合同.因此,dynamic_cast除了其他任何东西都需要修改客户端代码之外,你不可能做任何比这更快的事情.


小智 5

正如其他人所说,使用虚函数是一种很好的做法.使用它的另一个原因,不适用于你的情况,因为你不能添加音频,但我仍然值得一提 - 它可能比使用动态演员要快得多.在我用g ++完成的一些(不是非常严格的)测试中,虚函数比dynamic_cast高出4倍.

因为存在这样的差异,所以可能值得创建自己的继承层次结构,它包装了您无法控制的代码.您可以使用dynamic_cast(一次)创建包装器的实例,以决定要创建的派生类型,然后使用虚拟函数.