日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > c/c++ >内容正文

c/c++

C++ 基类和派生类的构造函数

發布時間:2025/3/12 c/c++ 39 豆豆
生活随笔 收集整理的這篇文章主要介紹了 C++ 基类和派生类的构造函数 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

在設計派生類時,對繼承過來的成員變量的初始化工作也要由派生類的構造函數完成,但是大部分基類都有 private 屬性的成員變量,它們在派生類中無法訪問,更不能使用派生類的構造函數來初始化。

解決辦法:在派生類的構造函數中調用基類的構造函數。

在派生類的構造函數中調用基類的構造函數:

#include<iostream> using namespace std;//基類People class People{ protected:char *m_name;int m_age; public:People(char*, int); }; People::People(char *name, int age): m_name(name), m_age(age){}//派生類Student class Student: public People{ private:float m_score; public:Student(char *name, int age, float score);void display(); }; //People(name, age)就是調用基類的構造函數 Student::Student(char *name, int age, float score): People(name, age), m_score(score){ } void Student::display(){cout<<m_name<<"的年齡是"<<m_age<<",成績是"<<m_score<<"。"<<endl; }int main(){Student stu("小明", 16, 90.5);stu.display();return 0; }

運行結果為:

小明的年齡是16,成績是90.5

請注意第 23 行代碼:

Student::Student(char *name, int age, float score): People(name, age), m_score(score){ }

People(name, age)就是調用基類的構造函數,并將 name 和 age 作為實參傳遞給它,m_score(score)是派生類的參數初始化表,它們之間以逗號,隔開。

也可以將基類構造函數的調用放在參數初始化表后面:

Student::Student(char *name, int age, float score): m_score(score), People(name, age){ }

但是不管它們的順序如何,派生類構造函數總是先調用基類構造函數再執行其他代碼(包括參數初始化表以及函數體中的代碼),總體上看和下面的形式類似:

Student::Student(char *name, int age, float score){People(name, age);m_score = score; }

當然這段代碼只是為了方便大家理解,實際上這樣寫是錯誤的,因為基類構造函數不會被繼承,不能當做普通的成員函數來調用。換句話說,只能將基類構造函數的調用放在函數頭部,不能放在函數體中

另外,函數頭部是對基類構造函數的調用,而不是聲明,所以括號里的參數是實參,它們不但可以是派生類構造函數參數列表中的參數,還可以是局部變量、常量等,例如:

Student::Student(char *name, int age, float score): People("小明", 16), m_score(score){ }

構造函數的調用順序

從上面的分析中可以看出,基類構造函數總是被優先調用,這說明創建派生類對象時,會先調用基類構造函數,再調用派生類構造函數,如果繼承關系有好幾層的話,例如:

A --> B --> C

那么創建 C 類對象時構造函數的執行順序為:

A類構造函數 --> B類構造函數 --> C類構造函數

構造函數的調用順序是按照繼承的層次自頂向下、從基類再到派生類的。

還有一點要注意,派生類構造函數中只能調用直接基類的構造函數,不能調用間接基類的。以上面的 A、B、C 類為例,C 是最終的派生類,B 就是 C 的直接基類,A 就是 C 的間接基類。

基類構造函數調用規則

通過派生類創建對象時必須要調用基類的構造函數,這是語法規定。換句話說,定義派生類構造函數時最好指明基類構造函數;如果不指明,就調用基類的默認構造函數(不帶參數的構造函數);如果沒有默認構造函數,那么編譯失敗。請看下面的例子:

#include <iostream> using namespace std;//基類People class People{ public:People(); //基類默認構造函數People(char *name, int age); protected:char *m_name;int m_age; }; People::People(): m_name("xxx"), m_age(0){ } People::People(char *name, int age): m_name(name), m_age(age){}//派生類Student class Student: public People{ public:Student();Student(char*, int, float); public:void display(); private:float m_score; }; Student::Student(): m_score(0.0){ } //派生類默認構造函數 Student::Student(char *name, int age, float score): People(name, age), m_score(score){ } void Student::display(){cout<<m_name<<"的年齡是"<<m_age<<",成績是"<<m_score<<"。"<<endl; }int main(){Student stu1;stu1.display();Student stu2("小明", 16, 90.5);stu2.display();return 0; }

運行結果:

xxx的年齡是0,成績是0。 小明的年齡是16,成績是90.5

創建對象 stu1 時,執行派生類的構造函數Student::Student(),它并沒有指明要調用基類的哪一個構造函數,從運行結果可以很明顯地看出來,系統默認調用了不帶參數的構造函數,也就是People::People()。

創建對象 stu2 時,執行派生類的構造函數Student::Student(char *name, int age, float score),它指明了基類的構造函數。

在第 27 行代碼中,如果將People(name, age)去掉,也會調用默認構造函數,第 37 行的輸出結果將變為:

xxx的年齡是0,成績是90.5

如果將基類 People 中不帶參數的構造函數刪除,那么會發生編譯錯誤,因為創建對象 stu1 時需要調用 People 類的默認構造函數, 而 People 類中已經顯式定義了構造函數,編譯器不會再生成默認的構造函數。

總結

以上是生活随笔為你收集整理的C++ 基类和派生类的构造函数的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。