天天看點

C++多态的實作方式總結

實作多态有兩種方法:

1、覆寫

***********

覆寫是指子類重新定義父類的虛函數的做法。

2、重載

***********

重載是指允許存在多個同名函數,而這些函數的參數表不同(或許參數個數不同,或許參數類型不同,或許兩者都不同)。

分析:

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

重載是在同一個類中相同的傳回類型和方法名,但是參數的個數和類型可以不同;而覆寫是在不同的類中。

其實,重載的概念并不屬于面向對象程式設計,重載的實作是:編譯器根據函數不同的參數表,對同名函數的名稱做修飾,然後這些同名函數就成了不同的函數。

比如有下面兩個同名函數:

function func(p:integer):integer;
function func(p:string):integer;
           

那麼編譯器做過修飾後的函數名稱可能是這樣的:int_func、str_func。

對于這兩個函數的調用,在編譯期間就已經确定了,是靜态的,稱為早期聯編。是以重載和多态無關。

真正和多态相關的是覆寫。當子類重新定義了父類的虛函數後,父類指針根據指派給它的不同的子類指針,動态的調用屬于子類的該函數,這樣函數調用在編譯期間是無法确定的,這樣的函數位址在運作期間綁定稱為動态聯編。

C++多态的實作方式總結

不要犯傻,如果它不是晚綁定,它就不是多态。

多态機制深入:

虛函數在C++中的實作機制就是用虛表和虛指針。也就是每個類用了一個虛表,每個類的對象用了一個虛指針。具體的用法如下:

class A
{public:
    virtual void f();
    virtual void g();
private:
    int a
};

class B : public A
{
public:
    void g();
private:
    int b;
};//A、B實作省略
           

因為A有virtual void f()和g(),是以編譯器為A類準備了一個虛表vtableA,内容如下:

A::f 的位址
A::g 的位址

B因為繼承了A,是以編譯器也為B準備了一個虛表vtableB,内容如下:

A::f 的位址
B::g 的位址

注意:因為B::g是重寫了的,是以B的虛表的g放的是B::g的入口位址,但是f是從上面的A繼承下來的,是以f的位址是A::f的入口位址。然後某處有語句 B bB;的時候,編譯器配置設定空間時,除了A的int a,B的成員int b;以外,還配置設定了一個虛指針vptr,指向B的虛表vtableB,bB的布局如下:

vptr : 指向B的虛表vtableB
int a: 繼承A的成員
int b: B成員

關于虛函數下面的講解下面部落格總結的也很好:

點選打開連結

參考維基百科補充些多态的知識:

多态是指計算機程式運作時,相同的消息可能會送給多個不同的類之對象,而系統可依據對象所屬類,引發對應類的方法,而有不同的行為。簡單來說,所謂多态意指相同的消息給予不同的對象會引發不同的動作稱之。

多态可分為變量多态與函數多态。變量多态是指:基類型的變量(對于C++是引用或指針)可以被指派基類型對象,也可以被指派派生類型的對象。函數多态是指,相同的函數調用界面(函數名與實參表),傳送給一個對象變量,可以有不同的行為,這視該對象變量所指向的對象類型而定。是以,變量多态是函數多态的基礎。

多态還可分為:

*************

動态多态:通過類繼承機制和虛函數機制生效于運作期。可以優雅地處理異質對象集合,隻要其共同的基類定義了虛函數的接口。在面向對象程式設計中,這被直接稱為多态。

*************

靜态多态:模闆也允許将不同的特殊行為和單個泛化記号相關聯,由于這種關聯處理于編譯期而非運作期,是以被稱為“靜态”。可以用來實作類型安全、運作高效的同質對象集合操作。C++ STL不采用動态多态來實作就是個例子。

*************

非參數化多态:

函數重載;運算符重載;帶變量的宏多态

*************

參數化多态:把類型作為參數的多态。在面向對象程式設計中,這被稱作泛型程式設計。

***********************************************************************************************************

對于C++語言,帶變量的宏和函數重載機制也允許将不同的特殊行為和單個泛化記号相關聯。然而,習慣上并不将這種函數多态、宏多态展現出來的行為稱為多态(或靜态多态),否則就連C語言也具有宏多态了。談及多态時,預設就是指動态多态,而靜态多态則是指基于模闆的多态。

最後來舉個例子:

比如有動物(Animal)之類(Class),而且由動物繼承出類雞(Chicken)和類狗(Dog),并對同一源自類動物(父類)之一消息有不同的響應,如類動物有“叫()”之動作,而類雞會“啼叫()”,類狗則會“吠叫()”,則稱之為多态。

哈哈~~~~~~~~~~~~~~~~

這下該對多态有個很好的認識了吧!!!!!!!!!!!!!!