1. 程式人生 > >C++筆記------類的繼承和多態

C++筆記------類的繼承和多態

eat 多態 虛函數表 height cte del 方法 自己 pro

從已有的類派生出新的類,叫繼承。派生類繼承了基類的特征和方法。
公有繼承:基類的公有成員成為派生類的公有成員;基類的私有成員成為派生類的一部分,但只能通過基類成員方法和保護方法訪問。
派生類構造函數,通過成員初始化列表的方式指明使用的基類構造函數,並傳遞基類信息。非構造函數不能使用初始化列表語法。

派生類可以使用基類不是私有的方法。

class A
{
private:
    int num;
public:
    int a;
public:
    A():a(10),num(1)
    {}
    void Show_num()
    {
        cout 
<< num <<endl; } ~A(){} }; class B:public A { public: int b; B():A(),b(5){} ~B(){} }; int main() { B b1; cout << b1.b <<" " << b1.a <<endl; b1.Show_num(); //b1只能通過基類公有方法訪問私有數據。 }

在派生類的對象創建中,首先是虛基類的構造函數,並按照聲明順序構造。然後是非虛基類的構造函數,
之後是成員對象的構造函數,最後是派生類自己的構造函數。
派生類對象過期先調用派生類析構函數,然後再調用基類析構函數。

class D1
{
public:
    D1()
    {
        cout << "D1 create" <<endl;
    }
    ~D1()
    {
        cout <<  "D1 free \n";
    }
};
class D2
{
public:
    D2()
    {
        cout << "D2 create" <<endl;
    }
    ~D2()
    {
        cout <<  "D2 free \n";
    }
};
class D3 { public: D3() { cout << "D3 create" <<endl; } ~D3() { cout << "D3 free \n"; } }; class D4:public D1,virtual public D2 { public: D3 tt; D4():tt() { cout << "D4 create" <<endl; } ~D4() { cout << "D4 free \n"; } }; int main() { D4 tt; return 0; }

技術分享圖片

1.子類能給父類賦值(向上轉換),但父類不可以給子類賦值

2.基類的指針可以指向派生類,基類的引用可以引用派生類對象。但只能調用基類的方法。派生類指針和引用不可以指向基類和引用基類。重新定義基類方法將隱藏基類方法。

派生類可以使用作用域解析符來調用基類方法。

class D1
{
public:
    D1()
    {
        cout << "D1 create" <<endl;
    }
    void show()
    {
        cout << "D1 show"<< endl;
    }

void show1()
{
cout <<" D1 show1()\n";
}

~D1()

    {
        cout <<  "D1 free \n";
    }
};
class D2
{
public:
    D2()
    {
        cout << "D2 create" <<endl;
    }
    void show()
    {
        cout << "D2 show" <<endl;
    }
    ~D2()
    {
        cout <<  "D2 free \n";
    }
};
class D4:public D1,virtual public D2
{
public:
    D4():tt()
    {
        cout << "D4 create" <<endl;
    }
    void show()
    {
        cout << "D4 show" <<endl;
    }

void show1(int i)
{
cout << i <<" D4 show1()\n";
}

~D4()
    {
        cout <<  "D4 free \n";
    }
};
int main()
{
    D4 tt;
    D2 t2;
    D1 t1;
    t1 = tt; 
    //tt = t1;  //報錯 
    D2* t3 = &tt;
    D1 & t4=tt; 
    t3->show();      //調用D2的show函數
    t4.show();        //調用D1的show函數
    tt.show();        //調用D1的show函數
    tt.D1::show();  //調用D1的show函數
    //tt.show1();   //報錯,顯示沒有show1()函數
tt.show1(2);
return 0; }

多態:根據調用的對象具有不同行為。

主要實現機制是1.重新定義基類方法 2.使用虛方法
使用virtual,程序根據引用或指針的對象選擇方法。沒有virtual,則根據引用或指針類型調用方法。
方法在基類中定義為虛方法它在派生類中自動成為虛方法,vistual只用在類聲明的方法原型中。
將基類的析構函數定義為虛析構函數,為了保護讓程序正確調用析構函數。
編譯器對非虛方法采用靜態聯編,對虛方法采用動態聯編。靜態聯編效率比動態聯編高。
編譯器處理虛函數是為對象添加一個隱藏成員,該成員保存了指向函數的地址數組的指針,稱為虛函數表。
友元不能是虛函數,因為友元不是類成員,只有類成員才能是虛函數。
private與protected區別
  派生類成員可以直接訪問基類保護成員,但不能直接訪問基類私有成員。
  保護訪問控制讓派生類能夠訪問公眾不能使用的內部函數。
純虛函數,可以不提供實現代碼。

virtual void show() = 0 ;

抽象基類(ABC)包含純虛函數的類,不能創建對象。

C++筆記------類的繼承和多態