C++中要想在運行時獲取類型信息,可沒有Java中那麼方便,Java中任何一個類均可以經過反射機制來獲取類的基本信息(接口、父類、方法、屬性、Annotation等),並且Java中還提供了一個關鍵字,能夠在運行時判斷一個類是否是另外一個類的子類或者是該類的對象,但C++卻沒有這麼多功能,C++中得到類信息只能經過RTTI機制,並且功能仍是頗有限的,由於C++中最終生成的代碼是直接與機器相關的,而Java中會生成字節碼文件,再由JVM加載運行,字節碼文件中能夠含有類的信息。ide
C++中RTTI的簡單源程序示例:函數
class A{ private: int a; }; class B{ public: //加一個虛函數 virtual void f(){} }; class C:public B { public : void f(){}; }; class D:public A { public: void f(){} }; int main() { int a=2; //打印出int cout<<typeid(a).name()<<endl; A objA; //打印出class A cout<<typeid(objA).name()<<endl; B objB; //打印出class B cout<<typeid(objB).name()<<endl; C objC; //打印出class C cout<<typeid(objC).name()<<endl; /* //如下是多態在VC 6.0編譯器不支持,可是在GCC以及微軟更高版本的編譯器卻都是 //支持的,且是在運行時候來肯定類型的,而不是在編譯器,會打印出class c B *ptr=new C(); cout<<typeid(*ptr).name()<<endl; */ A *ptr=new D(); //打印出class A而不是class D cout<<typeid(*ptr).name()<<endl; return 0; }
要想理解上述代碼:咱們須要明白如下幾個事實spa
1:typeid是一個關鍵字對象
2:typeid的結果有時候在編譯期肯定有時間會在執行期肯定接口
3:typeid運行時,會將判斷的結果存儲在一個consttypeinfo&對象中ip
4:不一樣的編譯器對typeid運算的結果差別很大,例如在VC 6.0與G++編譯器中,G++編譯器支持運行時動態肯定類型,而VC 6.0則不支持。編譯器
1:typeid是一個關鍵字,能夠在任意一本C++入門書中看到,typeid是一個關鍵字,像Sizeof同樣,要是函數的話,函數傳參你有見過這樣的嗎typeid(int),直接傳int,而不是傳一個整型值的,我是沒見過:)it
2:看看上述的程序,你會發現上述程序中除了多態的那一部份(在VC 6.0中是沒法編譯經過的),其餘的均是在編譯期運行,多態的會在執行期去運行,爲了更具說服務力,看看下面的代碼,是上面程序的部分彙編代碼:io
30: //打印出int 31: const type_info &t=typeid(a);//從下面的彙編代碼中能夠看出類型在編譯期就已經肯定了 004011C4 mov dword ptr [ebp-14h],offset int `RTTI Type Descriptor' (00441e08) 32: cout<<t.name()<<endl; 004011CB push offset @ILT+35(std::endl) (00401028) 004011D0 mov ecx,dword ptr [ebp-14h]
從上面的程序,能夠看出對於不是多態類型的,直接在編譯器就解決了類型的肯定,這樣有利於減小程序的運行時間編譯
對於多態類型:
未完,明天再寫吧