我們在定義對象的時候,會發現很多的對象之間都是有聯系的,如以下兩個類:
class Person{public: void eat(); string m_strName; int m_iAge;};class Worker{public: void eat(); void work(); string m_strName; int m_iAge; int m_iSalary;};worker中的一些成員也是person的成員,應對這種情況,為了減輕程序員的工作量,C++設計了繼承。 有了繼承,我們可以把worker類寫成下面那樣,不必把person類再寫一遍。其中worker是person的派生類,person是worker的 基類。
class Worker:public Person{public: void work(); int m_iSalary;};這里有一個需要知道的,我們在實例化一個派生類的對象時,會先構造基類,再構造派生類,而析構時則順序相反,具體的順序如下 person() worker() ~worker() ~person()
C++的繼承方式有3種 class A::public B//公有繼承 class A::PRotected B//保護繼承 class A::private B//私有繼承
其中protected在不涉及到繼承關系時,其特性和private的性質是一樣的。
class Person{public: Person();//構造函數 ~Person();//析構函數 void eat(); protected: int m_iAge;private: string m_strName;};當做如下訪問時,會出現錯誤,因為賦值的不在public下
int main(){ Person person; person.eat(); person.m_iAge = 20;//錯誤 person.m_strName = "jim";//錯誤 return 0;}當在繼承時,做如下定義
class Person{public: Person();//構造函數 ~Person();//析構函數 void eat(); protected: int m_iAge; string m_strName;};當為protected時,相關的對象成員能夠繼承到如下位置。其中void work()能夠訪問繼承來的m_iAge
class Worker :public Person//公有繼承{public: Worker();//構造 ~Worker();//析構 void eat();//繼承person的 void work(){ m_iAge = 20; }protected: string m_strName;//繼承person int m_iAge;//繼承person int m_iSalary;};如果將以上代碼中的protected換成private,代碼如下
class Person{public: Person();//構造函數 ~Person();//析構函數 void eat(); private: int m_iAge; string m_strName;};class Worker :public Person//公有繼承{public: Worker();//構造 ~Worker();//析構 void eat();//繼承person的 void work(){ m_iAge = 20; }//這樣訪問錯誤private: //private中的m_strName和m_iAge被繼承到了不可見位置 int m_iSalary;};此時的void work()不可調用繼承來的m_iAge,因為private中的m_strName和m_iAge被繼承到了不可見位置。
總結一下 1.當兩個類產生了繼承關系,而繼承方式是public,那么基類下的public成員會被繼承到派生類的public下面;基類下的protected成員會被繼承到派生類的protected成員下;基類的privated成員將會無法訪問。 2.當兩個類產生了繼承方式,而繼承方式是protected,那么基類下的public成員會被繼承到派生類的protected下面;基類下的protected成員會被繼承到派生類的protected成員下;基類的privated成員將會無法訪問。 3.當兩個類產生了繼承關系,而繼承方式是private,那么基類下的public成員會被繼承到派生類的private下面;基類下的protected成員會被繼承到派生類的private成員下;基類的privated成員將會無法訪問。
C++中有兩個很容易的混淆概念:覆蓋和隱藏。那么什么是隱藏?假如B是A的派生類,兩個類有相同函數名的成員函數,比如void ABC(),這時,子類中的void ABC()會自動隱藏父類中的void ABC(),但并沒有消失,可以通過特殊的手段訪問,數據成員也有隱藏這種現象。那么什么是覆蓋呢?如果我們沒有在子類中定義同名的虛函數,那么在子類虛函數表當中就會寫上父類當中那個虛函數的函數入口地址,如果我們在子類中也定義了同名的虛函數,那么在子類的虛函數表當中,我們就會把原來父類的虛函數的函數地址覆蓋一下,覆蓋成子類的虛函數的函數地址【關于虛函數表涉及請看多態的實現原理篇】
新聞熱點
疑難解答
圖片精選