c 多型與虛函式

2021-08-21 02:50:24 字數 3993 閱讀 4784



多型按字面的意思就是多種形態。當類之間存在層次結構,並且類之間是通過繼承關聯時,就會用到多型。

c++ 多型意味著呼叫成員函式時,會根據呼叫函式的物件的型別來執行不同的函式。

下面的例項中,基類 shape 被派生為兩個類,如下所示:

#include using namespace std;

class shape

int area()

當上面的**被編譯和執行時,它會產生下列結果:

parent class area

parent class area

導致錯誤輸出的原因是,呼叫函式 area() 被編譯器設定為基類中的版本,這就是所謂的靜態多型,或靜態鏈結 - 函式呼叫在程式執行前就準備好了。有時候這也被稱為早繫結,因為 area() 函式在程式編譯期間就已經設定好了。

但現在,讓我們對程式稍作修改,在 shape 類中,area() 的宣告前放置關鍵字 virtual,如下所示:

class shape 

virtual int area()

// pure virtual function

virtual int area() = 0;

};= 0 告訴編譯器,函式沒有主體,上面的虛函式是純虛函式。

多型性:指乙個名字,多種語義;或介面相同,多種實現。

過載函式是多型性的一種簡單形式。

虛函式允許函式呼叫與函式體的聯絡在執行時才進行,稱為動態聯編。

虛函式:

冠以關鍵字

virtual 

的成員函式稱為虛函式。

基類指標

實現執行時多型的關鍵首先是要說明虛函式,另外,必須用呼叫派生類的不同實現版本。

虛函式與基類指標

基類指標雖然獲取派生類物件位址,

卻只能訪問派生類從基類繼承的成員

例:

#include

using

namespace

std ;

class

base

void

who()

protected:

char x;

} ;class

first_d :

public base

void

who()

protected:

char y;

} ;class

second_d :

public first_d

void

who()

protected:

char z;

} ;int

main

()

執行結果:

base class: a

base class: t

base class: e

first derived class: t.o

second derived class: e.  n . d

[注意]

ø乙個虛函式,在派生類層介面相同的過載函式都保持虛特性

ø  虛函式必須是類的成員函式

ø不能將友元說明為虛函式,但虛函式可以是另乙個類的友元

ø析構函式可以是虛函式,但建構函式不能是虛函式

虛函式的過載特性

ø在派生類中過載基類的虛函式要求函式名、返回型別、引數個數、

引數型別和順序完全相同

ø如果僅僅返回型別不同,c++認為是錯誤過載

如果函式原型不同,僅函式名相同,丟失虛特性

例:

class

base

;class

derived :

public base

;void

g( )

;虛析構函式

建構函式不能是虛函式

。建立乙個派生類物件時,必須從類層次的根開始,沿著繼承路徑逐個呼叫基類的建構函式。

析構函式可以是虛的

。虛析構函式用於指引delete 運算子正確析構動態物件。

例:普通析構函式在刪除動態派生類物件的呼叫情況

#include

using

namespace

std ;

class

a

} ;class

b :public a

} ;int

main

()

執行結果:

delete first object:

a::~a()is called.

deletesecond object:

b::~b()is called.

a::~a()is called.

[說明]

(1)派生類應該從它的基類

公有派生。(2

)必須首先在基類中定義虛函式

。(3)派生類對基類中宣告虛函式重新定義時,關鍵字virtual可以不寫。

(4)一般通過

基類指標訪問虛函式

時才能體現

多型性。

(5)乙個虛函式無論被繼承多少次,保持其虛函式特性。

(6)虛函式必須是其

所在類的成員函式

,而不能是友元函式,也不能是靜態函式。(7)

建構函式、內聯成員函式、靜態成員函式不能是虛函式

。(虛函式不能以內聯的方式進行處理)

(8)析構函式可以是虛函式,通常宣告為虛函式。

6.成員函式呼叫虛函式(採用動態聯編)

#include

class

a

double

funb

(double x)

};class

b:public a

}; class

c:public b

};void

main

()

執行結果:

funa of class c called.

13.5

funa of class b called.

9純虛函式和抽象類

(1)概念:純虛函式是一種特殊的虛函式,

(2)功能:在許多情況下,在基類中不能對虛函式給出有意義的實現,而把它宣告為純虛函式,它的實現留給該基類的派生類去做。

(3)純虛函式是乙個在基類中說明的虛函式,在基類中沒有定義,要求任何派生類都定義自己的版本。

純虛函式為各派生類提供乙個公共介面

純虛函式說明形式:

virtual 

型別函式名(參數列)= 0 ;

乙個具有純虛函式的基類

稱為抽象類。

例:

#include

using

namespace

std ;

class

number

virtual

void

show

()=

0 ;protected:

int val ;

};class

hex_type :

public number

void

show

()

};class

dec_type :

public number

void

show

()

};class

oct_type :

public number

void

show

()

}; void

fun( number & n )

// 抽象類的引用引數

intmain

()

C 虛函式與多型

1.1 虛函式概念 1.定義 在乙個類的成員函式前面加上virtual關鍵字,則該函式就稱為虛函式。2.如果乙個函式不是類的成員函式,則該函式不能定義為虛函式。即就是類外面不能使用virtual關鍵字 1.2 純虛函式與抽象類 1.純虛函式 在虛函式的後面加上 0 virtual void disp...

C 多型與虛函式

這一篇介紹一下 c 物件導向三大特徵之一的多型 之前面試某大廠的實習生被問到多型,後來又了解到一些設計模式,才體會到多型的強大,在這裡把對多型的一點點淺顯認識總結一下 虛表 class test cout sizeof test endl test p new test p vfunc 將類指標p強...

虛函式與多型 C

引用和指標的靜態型別 編譯時可知的引用型別或指標型別 和動態型別 指標或引用所繫結的物件的型別,執行時獲知 可以不同。因此,可以用基類的指標或引用指向派生類的物件,再通過基類的指標或引用來呼叫虛函式,所執行的虛函式是引用或指標所指向的物件所屬型別定義的版本。c 函式預設不使用動態繫結,除非滿足兩個條...