2013-04-28 73 views
2

我是一位研究高級C++主題的新手,所以如果問題聽起來太明顯,請原諒我。使用typeid實現RTTI

我一直在閱讀有關各種方法,通過它們我們可以在運行時以C++(通常稱爲RTTI)獲取對象類型的信息。

但是,我很困惑它是如何工作的。 我讀過一些RTTI解釋時經常提到的東西。其中之一是動態使用dynamic_cast <>將對象強制轉換爲其他對象。另一個是在運行時使用typeid來確定對象的類型。

我想知道使用typeid是否是在C++中實現RTTI的正確方法,如果是,那麼typeid操作符在運行時如何確定對象的類型(是否分析在內存中的對象blob?)

如果使用typeid不是正確的方式,那麼請爲其實現提供其他方法。

+0

它看起來像你倒退了。 'typeid'可以工作,因爲RTTI是在編譯器中實現的,所以詢問是否使用'typeid'「來實現RTTI」看起來很混亂。 「實施RTTI」是什麼意思? – 2013-04-28 18:40:44

+0

你試圖解決什麼問題讓你覺得你需要RTTI和/或typeid? – quamrana 2013-04-28 18:41:31

+2

C++ RTTI系統是[反射](http://en.wikipedia.org/wiki/Reflection_%28computer_programming%29)的一個非常差和功能較少的變體。我個人的觀點是,無論使用哪種語言,都應儘可能避免設計中的任何反射需求。 – 2013-04-28 18:43:17

回答

6

重要:
理想的情況下,如果你需要確定你需要重新審視你的設計對象的類型,因爲很有可能你錯過了什麼那裏,你違反了OOP的SOLID規則。

C++標準提供了dynamic_casttypeid作爲確定對象的類型的兩種方式。兩者都有其優點和侷限性。他們如何識別類型是一個實現相關的細節,但通常他們通過維護指向對象vtable中的類型信息結構的指針來實現。如果你完全不知道vtable是什麼,Marshal Clines C++ Faq提供了一個很好的解釋here

你可以在使用的大多數編譯器的實現細節,
Technical Report on C++ Performance

有關摘錄:

5.3.7類型信息

給出一個多態類的對象(至少具有一個虛函數的類),則可以通過使用typeid運算符來獲取type_info對象。在 原理中,這是一個簡單的操作,它涉及通過查找虛擬函數表 ,通過查找對象所屬的派生類最多的類對象,然後從該對象的虛擬函數表中提取指向type_info對象的指針(或相當於 )。


5.3.8動態角色

給定一個指針指向一個多態類的一個對象,流延到一個指針到另一個基站 子對象相同的派生類對象可以做到使用dynamic_cast。在 原理中,該操作涉及通過找到對象所屬的派生最多的類對象,然後使用與該對象相關聯的類型信息 來確定是否允許轉換(強制轉換),來查找虛擬函數表,最後 執行該指針的任何必需的調整。原則上,這種檢查 涉及描述最衍生的 類的基類的數據結構的遍歷。因此,dynamic_cast的運行時成本可能取決於所涉及的兩個類的類層次結構中的相對位置 。

1

RTTI僅適用於具有虛擬功能的類的實例。在這種情況下,編譯器會向類中添加一個特殊成員,調用虛擬表指針。每個具有虛函數的類都有自己的虛表。通過檢查指向哪個虛擬表,可以確定對象的具體類型。