在C++中 , 若有兩個derived class 繼承同一個abstract base class時 ,
我們若以base class pointer (or reference )來接derived class的instance , 並使用base class的pointer
做為virtual function的argument傳入時 , 對於這個argument我們通常沒辦法知道他的type .
for example :
Shape* s1 = new Circle();
Shape* s2 = new Square();
bool b = s1.intersectWith(s2); // we can't know the type of s2.
而要解決這個問題 , 就我們目前所知道的 , 可以使用double dispatching , 或typeid兩種方法 .
而除了這兩種方法 , 我們還可以使用dynamic_cast在run time時做強制轉型確認 (用來將一個基底類別的指標強制轉型到derived class的pointer).
( dynamic_cast can be used only with pointers and references to objects.
Its purpose is to ensure that the result of the type conversion is a valid complete object of the requested class) -- from ref1
以上面的example來說:
bool judge = dynamic_cast<Square* > (s2);
其中dynamic_cast<>會先判斷s2是否符合Square class的type ,
若true則轉型並return 1,
否則就不轉型並return 0.
for example :
#include <iostream>
#include <exception>
using namespace std;
class CBase { virtual void dummy() {} };
class CDerived: public CBase { int a; };
int main ()
{
try
{
CBase * pba = new CDerived;
CBase * pbb = new CBase;
CDerived * pd;
pd = dynamic_cast<CDerived*>(pba);
if (pd==0) cout << "Null pointer on first type-cast" << endl;
pd = dynamic_cast<CDerived*>(pbb);
if (pd==0) cout << "Null pointer on second type-cast" << endl;
}
catch (exception& e)
{
cout << "Exception: " << e.what();
}
return 0;
}
Even though both are pointers of type CBase*, pba points to an object of type CDerived,
while pbb points to an object of type CBase.
(如果使用參考的話,dynamic_cast在轉換失敗之後會丟出bad_cast例外,所以您必須使用try...catch來處理例外)
ref : http://www.cplusplus.com/doc/tutorial/typecasting/
ref : http://caterpillar.onlyfun.net/Gossip/CppGossip/dynamicCast.html