從C看C++之(五)繼承和派生

 在實際的編程中,我們會遇到下面一種場景:

 我們已經有一個類A:

class Student
{
private:
    int num;
     char name[30];
     char sex;

 public:                             
    void display( )
    {
       cout<<"num: "<<num<<endl;
       cout<<"name: "<<name<<endl;
       cout<<"sex: "<<sex<<endl;
    } 
};
    這時候,我們需要另外一個類B:

class Studend1
{   
private: 
    int num;          //此行原來己有
    char name[20];       //此行原來己有
    char sex;         //此行原來己有
    int age;
    char addr[20];

 public:            
   void display()         //此行原來己有
    {
        cout<<"num: "<<num<<endl;    //此行原來己有
        cout<<"name: "<<name<<endl;//此行原來己有
        cout<<"sex: "<<sex<<endl;      //此行原來己有
        cout<<"age: "<<age<<endl;
        cout<<"address: "<<addr<<endl;}                 
}; 
    通過比較類A和類B,我們可以發現,類B很多代碼是和類A複用了的,相對於類A而言,類B只是增加了一些相關的成員及改動了一下方法.

 繼承和派生,就是爲了解決這種場景出現了.它可以提高代碼的複用.

  在C++中所謂“繼承”就是在一個已存在的類的基礎上建立一個新的類.已存在的類稱爲“基類(base class)”或“父類(father class)”.
新建立的類稱爲“派生類(derived class)”或“子類(son class)”. 
    因此,通過下面的形式,我們就可以達到我們的目的:

class Student1: public Student//聲明基類是Student
{
private:
    int age;    //新增加的數據成員
    string addr;  //新增加的數據成員

public:
   void display_1()  //新增加的成員函數
   {  
        cout<<"age: "<<age<<endl; 
        cout<<"address: "<<addr<<endl;
   }   
};
    通過繼承機制,利用舊的已有的數據成員定義新的數據成員.新數據成員不僅有新定義的數據成員,還同時有舊數據成員.

 從父類派生子類的形式如下:

class  ClassName:<Access>BaseClassName
    其中,Access的取值有public、protect和private.如下:

 根據Access取值不一樣,派生分爲公有派生(public)、保護派生(protect)和私有派生(private).不同的派生方式繼承過來父類的數據成員也是不同的.


公有派生:

基類中所有成員在派生類中保持各個成員的訪問權限.
    如下圖所示:

私有派生:

  基類中公有成員和保護成員在派生類中均變爲私有的,在派生類中仍可直接使用這些成員,基類中的私有成員,在派生類中不可直接使用.
    如下圖所示:

保護派生:

保護派生時,基類中公有成員和保護成員在派生類中均變爲保護的和私有的,在派生類中仍可直接使用這些成員,基類中的私有成員,在派生類中不可直接使用.
    如下圖所示:

小結:

    一般而言,我們比較關心的是派生類.而派生類肯定也是需要用到基類的一些數據,否則我們派生出一個類也是意義不大.因此,我們也要關心派生類對基類的數據成員的訪問.
從上述可知,除了基類的私有數據成員,派生類在類內都可以直接訪問.至於繼承過來基類的數據成員的訪問屬性,可以用下面簡記:"公有不變,保護降級,私有不可問".


下面是C++的一個示例:

源碼:

#include <iostream>

using namespace std;

class baseClass
{
private:
	unsigned int age;
	bool sex;
public:
	baseClass(unsigned int a,bool s)
	{
		age = a;
		sex = s;
	}

	~baseClass()
	{
		std::cout << "~Base Class"<< std::endl;
	}

	unsigned int baseGetAge(void);
	bool baseGetSex(void);	
};

unsigned int baseClass::baseGetAge(void)
{
	return age;
}

bool baseClass::baseGetSex(void)
{
	return sex;
}

class deriveClass:public baseClass
{
private:
	unsigned int score,number;
public:
	deriveClass(unsigned int a,bool se,unsigned int sc,unsigned int nu):baseClass(a,se)
	{
		score = sc;
		number = nu;
	}

	~deriveClass()
	{
		std::cout << "~derive Class" << std::endl;
	}

	unsigned int deriveGetAge(void);
	bool deriveGetSex(void);
	unsigned int deriveGetScore(void);
	unsigned int deriveGetNumber(void);
};

unsigned int deriveClass::deriveGetAge(void)
{
	return baseGetAge();
}

bool deriveClass::deriveGetSex(void)
{
	return baseGetSex();
}

unsigned int deriveClass::deriveGetScore(void)
{
	return score;
}

unsigned int deriveClass::deriveGetNumber(void)
{
	return number;
}

int main(void)
{
	deriveClass *cls = NULL;
	cls = new deriveClass(18,0,100,26);	

	std::cout << "Age = " << cls->deriveGetAge()<< std::endl;
	std::cout << "Sex = " << cls->deriveGetSex()<< std::endl;
	std::cout << "Score = " << cls->deriveGetScore()<< std::endl;
	std::cout << "Number = " << cls->deriveGetNumber()<< std::endl;

	delete cls;
	cls = NULL;

	return 0;
}
    編譯運行:

root@se7en-LIFEBOOK-LH531:~/learn/Cpp_Program# g++ class.cpp -o classTest
root@se7en-LIFEBOOK-LH531:~/learn/Cpp_Program# ./classTest 
Age = 18
Sex = 0
Score = 100
Number = 26
~derive Class
~Base Class
    涉及到的知識點:

1.繼承與派生的編程思想;
2.new對象和釋放;
3.通過派生類的構造函數去實現基類的構造函數.

抽象類:

    抽象類的定義:

當定義了一個類,這個類只能用作基類來派生出新的類,而不能用這種類來定義對象時,稱這種類爲抽象類.簡而言之,將類的構造函數或析構函數的訪問權限定義爲保護的時或者
包含一個或以上的純虛函數的類,這種類爲抽象類.需要注意的是,抽象類是不能用來定義對象的.


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章