c++虛擬函式和虛繼承
阿新 • • 發佈:2018-12-30
1.多繼承可能會出現奇葩現象,多個同樣的變數,導致子類不知道呼叫的那個變數來自哪個父類。
2.如果一個外部方法的引數是父類,那麼即使傳了一個子類,在方法中呼叫這個類的內部方法,不管你傳入的是子類還是父類,都會強行給你呼叫父類的方法。因為編譯器認為這樣是安全的,這個方法一定在父類中可以找得到,哪怕你子類也定義了自己的方法。
關鍵字virtual用於父類方法,如果傳了一個子類物件,並且子類重寫了父類的這個virtual方法,就會呼叫子類的方法。傳誰就呼叫誰,這個就是多型。我記得java是先在子類那裡找,沒有才回去父類。使用虛擬函式:
沒有使用:
不具備多型性
#include<iostream> using namespace std; class A { public: A() { //用x表示遇到A的預設建構函式 this->name = 'x'; } A(char name) { this->name = name; } virtual void run() { cout<<"A run ,actual object is:"<<this->name<<endl; } char name; }; //run方法用來測試多型 class B:virtual public A { public: B(char name):A(name) { this->name = name; } void run() { cout<<"B run ,actual object is:"<<this->name<<endl; } }; //虛繼承A class C:virtual public A { public: C(char name):A(name) { this->name = name; } void run() { cout<<"C run ,actual object is:"<<this->name<<endl; } }; //多繼承與虛繼承 //誰繼承在後,那麼會出現歧義的那個變數就歸誰管。 class D:public B,public C { public: D(char bname,char cname):B(bname),C(cname) { } //一定要重寫這個方法,不然run方法又要模稜兩可了 //反正不寫會報錯 void run() { cout<<"D run ,actual object is:"<<this->name<<endl; } }; void start(A& a) { a.run(); } int main() { A a('a'); B b('b'); D d('b','c'); start(a); start(b); //如果d的父類不採用虛繼承的方式繼承父類,那麼這裡會出現指代不明 cout<<b.name<<endl; //如果不虛繼承,就會報錯 cout<<d.name<<endl; //沒有父類虛繼承爺爺,子類就要向下面這麼寫 //cout<<d.B::name<<'\t'<<d.C::name<<endl; return 0; }