我們先定義乙個基類。
class
base
;virtual
~base()
void
no_static_member_function()
static
void
static_member_function()
virtual
void
virtual_member_function()
private
:int no_static_member_data;
static
int static_member_data;
};
這是乙個典型的非繼承的c++類,它的物件模型如下:
drived為base的派生類
class
drived1
:public base
virtual
~drived1()
virtual
void
virtual_member_function()
virtual
void
virtual_member_function2()
private
:int m1;
}
我們來看一下它的物件模型:
在c++物件模型中,對於一般繼承(這個一般是相對於虛擬繼承而言),若子類重寫(overwrite)了父類的虛函式,則子類虛函式將覆蓋虛表中對應的父類虛函式(注意子類與父類擁有各自的乙個虛函式表);若子類並無overwrite父類虛函式,而是宣告了自己新的虛函式,則該虛函式位址將擴充到虛函式表最後(在vs中無法通過監視看到擴充的結果,不過我們通過取位址的方法可以做到,子類新的虛函式確實在父類子物體的虛函式表末端)。而對於虛繼承,若子類overwrite父類虛函式,同樣地將覆蓋父類子物體中的虛函式表對應位置,而若子類宣告了自己新的虛函式,則編譯器將為子類增加乙個新的虛表指標vptr,這與一般繼承不同,在後面再討論。
drived2同時繼承base和base1
class
base1
;virtual
~base1()
void
no_static_member_function()
static
void
static_member_function()
virtual
void
virtual_member_function()
private
:int no_static_member_data1;
static
int static_member_data;};
class
drived2
:public base,
public base1
virtual
~drived2()
virtual
void
virtual_member_function()
private
:int md2;
};
我們來看一下它的物件模型:
此情況下由於靜態資料成員為私有,故在派生類中不會有不明確的情況,但靜態成員函式是public的,此時以派生類方式呼叫會產生定義不明確的錯誤。
對於基類的虛表都會被派生類overwrite覆蓋。
下一節討論虛繼承的c++物件模型
C 物件模型(一)
在c 中,有兩種類成員變數 static 和 nonstatic 三種類成員函式 static nonstatic 和 virtual 如 class point 簡單物件模型 圖1 簡單物件模型 在這個模型中,乙個object是一些列的slots,每乙個slot指向乙個成員,成員按其宣告次序,各被...
C 物件模型筆記 一 C 物件
c 支援了資料和方法的聯絡。對 c 來說,他的布局成本就是 1.none static data member 2.a pointer to virtue table 3.the pointer to virtue class 而成員函式,並不包括在 c 物件裡。還而言之,每乙個非 inline 成...
c 物件模型分析(一)
深夜睡不著覺,很痛苦。關於物件 第一部分 1.c 加上封裝之後的成本 a.成員資料 c class中的成員資料等同於c中struct中的資料 c.內聯的成員函式 擁有乙個或零個函式定義的內聯函式會在每個使用者身上產生乙個函式實體 d.virtual function機制 支援乙個有效率的 執行期繫結...