標籤:copy 總結 提示 nbsp book 函數 預設 建構函式 none
參考:http://www.weixueyuan.net/view/6364.html
總結:
衍生類別建構函式可以自動調用基類的預設建構函式而無需顯式調用。
生類建構函式可以自動調用基類的預設建構函式,但是前提是預設建構函式必須存在。
當基類沒有預設建構函式時,衍生類別則無法自動調用基類的預設建構函式了。遇到這種情況有兩種解決方案:其一,在基類中定義一個預設建構函式(不帶參數的建構函式),例如上一節中的例2;其二,衍生類別中的每一個建構函式都顯式的調用基類中的帶參建構函式。
建議在設計類的時候為每一個類設計一個預設建構函式,畢竟預設建構函式並不會妨礙建構函式的顯式調用。
在建立衍生類別對象時,必須顯式或隱式地調用基類的某一個建構函式
衍生類別建構函式可以自動調用基類的預設建構函式而無需顯式調用。例如在上一節例2中,我們如果將condingbook類中的預設建構函式codingbook():book(){lang = none;}語句修改為codingbook(){lang = none;},則這個程式運行結果依然保持不變,因為衍生類別的建構函式會自動調用基類的預設建構函式。
派生類建構函式可以自動調用基類的預設建構函式,但是前提是預設建構函式必須存在。通常情況下,預設建構函式系統會自動產生的,但是如果在基類中,我們自己定義了一個帶參數的建構函式,這個時候,系統是不會為基類自動產生預設建構函式的,這個時候衍生類別則無法自動調用基類的預設建構函式了,因為基類根本就不存在預設建構函式。遇到這種情況有兩種解決方案:其一,在基類中定義一個預設建構函式(不帶參數的建構函式),例如上一節中的例2;其二,衍生類別中的每一個建構函式都顯式的調用基類中的帶參建構函式。
例1:
class base{public: base(int a){x = a; y = 0;} base(int a, int b){x = a; y = b;}private: int x; int y;};class derived: public base{public: derived(){z = 0;} derived(int c){z = c;}private: int z;};
我們來看一下這個例子,這個例子裡面先定義了一個類base作為基類,基類中擁有兩個成員變數x和y,同時定義了兩個帶參數的建構函式,兩個都是帶參建構函式,如此一來類base就不會自動產生預設建構函式了。再來看衍生類別定義,衍生類別中新增了成員變數z,並且定義了一個帶參建構函式和一個預設建構函式。但是如此定義,編譯器會提示法錯誤,因為衍生類別的建構函式沒有顯示調用基類建構函式。解決這個問題的方法在上面說了,一個是在基類自己定義一個預設建構函式,另外一種方法是顯示調用基類建構函式。當然在設計類的時候推薦使用後者,畢竟建構函式就是為了初始化成員變數的,如果不顯式調用基類建構函式,則從基類中繼承過來的成員變數將得不到初始化,這一般來說都不是我們所希望看到的。
同時,我們還建議在設計類的時候為每一個類設計一個預設建構函式,畢竟預設建構函式並不會妨礙建構函式的顯式調用。通常我們還會遇到這樣一種情況,衍生類別中並未顯式定義建構函式,這個時候衍生類別中只有系統自動產生的預設建構函式,如此一來,如果我們不為基類設計一個預設建構函式,則程式就會編譯出錯。這種錯誤很玄妙,如果不小心還真是難以發現。為了避免這種情況的發生,我們建議為每一個類設計一個預設建構函式。
根據以上兩點建議,我們將例1進行修改,正確代碼如下。
例2:
複製格式化新視窗
#include<iostream>using namespace std;class base{public: base(){x = 0; y = 0;} base(int a){x = a; y = 0;} base(int a, int b){x = a; y = b;}private: int x; int y;};class derived: public base{public: derived():base(){z = 0;} derived(int a, int b, int c):base(a,b){z = c;}private: int z;};int main(){ derived A; derived B(1,2,3); return 0;}
在這個例子中,我們將例1中出現的問題採用雙管齊下的方式解決了,為基類定義了預設建構函式,並且在衍生類別中顯式地調用基類中的建構函式。
總的來說,在建立衍生類別對象時,必須顯式或隱式地調用基類的某一個建構函式,這一點非常重要。當然被調用的基類的建構函式可以是帶參建構函式,也可以是預設建構函式。
3.7 C++衍生類別建構函式調用規則