class B { public: void mf(); ... }; class D: public B {...};
對於以下行爲:ide
D x; B *pB = &x; pB->mf(); //和以下的代碼 D *pD = &x; pD->mf();
如上調用的兩個mf()理應是相同的,可是若是mf()是個虛函數並且D有本身的mf版本,那就有問題了:函數
class D: public B { public: void mf();//hides B:mf(); ... }; pB->mf(); //B::mf() pD->mf(); //D::mf()
上面兩種狀況出現的緣由是,非虛函數B::mf和D::mf都是靜態綁定(statically bound)的,也就是說,因爲pB被聲明爲pointer-to-B,經過pB調用的非虛函數永遠是B所定義的版本,即便pB指向一個類型爲派生類的對象。spa
虛函數是動態綁定(dynamically bound)的,若是mf是個虛函數,不論經過pB或是pD調用mf,都會調用D::mf,由於pB和pD真正指的都是一個類型爲D的對象。code
解決:若是D真的想要出現與B不同的mf,那就把mf聲明爲virtual吧。對象
牢記:public繼承意味着父類子類是一種is-a的關係。blog