C 物件構造與析構以及記憶體布局

2021-06-13 06:52:57 字數 3782 閱讀 5390

主要**物件的構造順序與記憶體的布局,主要參考**為《exceptional c++ style中文版》

文中第十四條 順序!順序!根據文中的**摘錄如下,**中新增了一些除錯的資訊。

#include struct classcomp 

virtual ~b1()

virtual ~v1()

virtual ~d1()

virtual ~b2()

virtual ~b3()

virtual ~v2()

virtual ~d2()

virtual ~m1()

virtual ~m2()

virtual ~x()

以上程式的執行結果為:

constructor b1 005f7f94

constructor v1 005f7f94

constructor b1 005f7f98

constructor b2 005f7f9c

constructor v2 005f7f98

constructor d1 005f7f88

constructor b3 005f7f80

constructor d2 005f7f80

constructor m1 005f7f8c

constructor m2 005f7f90

constructor x 005f7f80

--------------------------------------------

0x5f7f80  constructor b3

0x5f7f80  constructor d2

0x5f7f80  constructor x

0x5f7f88  constructor d1

0x5f7f8c  constructor m1

0x5f7f90  constructor m2

0x5f7f94  constructor b1

0x5f7f94  constructor v1

0x5f7f98  constructor b1

0x5f7f98  constructor v2

0x5f7f9c  constructor b2

--------------------------------------------

destructor x 005f7f80

destructor m2 005f7f90

destructor m1 005f7f8c

destructor d2 005f7f80

destructor b3 005f7f80

destructor d1 005f7f88

destructor v2 005f7f98

destructor b2 005f7f9c

destructor b1 005f7f98

destructor v1 005f7f94

destructor b1 005f7f94

可以看出物件的構造順序和書中提示到的順序一致

類圖1.首先構造虛基類子物件

2.其次構造非虛基類子物件.

3.構造成員本身

4.構造物件本身

以上同等級的構造順序遵循從左到右的申明順序。

但是問題出現了

問題1:這個物件x的物件記憶體分布是這個樣子的。看上去位址是倒著分配的。首位址相近的並不是最先分配的那個物件。是個問題。。。大家可以考慮一下到底怎麼分布啊???我的編譯平台是vs2010

問題2:假如說類b1中含有某個方法,那麼x物件呼叫的是哪塊記憶體上的函式呢??

我猜是左邊的那個。廢話少說寫測試**。

改造一下後編譯竟然發現編譯問題

1>e:\opensource\exceptional c++ style\example_014class\example_014class.cpp(191): error c2385: ambiguous access of 'fun'

1>          could be the 'fun' in base 'b1'

1>          or could be the 'fun' in base 'b1'

看樣子編譯器他決定不了x物件將會呼叫記憶體中哪塊b1的函式。

是否就沒有辦法了呢?

想起物件模型的那本曾提到這種情況下使用 virtual的繼承 。果然請看改造後的**。

#include struct classcomp 

virtual ~b1()

virtual ~v1()

virtual ~d1()

virtual ~b2()

virtual ~b3()

virtual ~v2()

virtual ~d2()

virtual ~m1()

virtual ~m2()

virtual ~x()

執行結果:

constructor b1 00127f94

constructor v1 00127f98

constructor b2 00127f9c

constructor v2 00127f9c

constructor d1 00127f88

constructor b3 00127f80

constructor d2 00127f80

constructor m1 00127f8c

constructor m2 00127f90

constructor x 00127f80

--------------------------------------------

fun b1 00127f94

--------------------------------------------

0x127f80  constructor b3

0x127f80  constructor d2

0x127f80  constructor x

0x127f88  constructor d1

0x127f8c  constructor m1

0x127f90  constructor m2

0x127f94  constructor b1

0x127f98  constructor v1

0x127f9c  constructor b2

0x127f9c  constructor v2

--------------------------------------------

destructor x 00127f80

destructor m2 00127f90

destructor m1 00127f8c

destructor d2 00127f80

destructor b3 00127f80

destructor d1 00127f88

destructor v2 00127f9c

destructor b2 00127f9c

destructor v1 00127f98

destructor b1 00127f94

發現類b1還少構造了一次。哈哈~~果然很強大啊。。

c 構造與析構

c 中還提供了一些封裝方法 構造方法 析構方法 一 在宣告乙個類的物件後,要對該物件進行初始化,即對物件中的資料成員賦值 建構函式 用於建立乙個物件,提供初始化該物件的簡單手段 函式語法 建構函式的函式名必須與類名相同 它沒有返回值 作用為初始化物件 其呼叫是在宣告物件時候自動呼叫 python中的...

構造 析構 物件與繼承

c 學習筆記之二 上一節講到了建構函式,這一節繼續講解。1 建構函式可以被過載,如 object object int object 這兩個函式是具有相同的函式名,而引數個數或引數型別不同,這就是過載。2 析構函式 特點 沒有返回值,以 打頭,且函式在物件銷毀時呼叫 即作用域結束時被呼叫 出了作用域...

物件的構造與析構

建立乙個物件時,常常需要作某些初始化的工作,例如對資料成員賦初值。注意,類的資料成員是不能在宣告類時初始化的。原因 類相當於乙個模板,是一種新資料型別,而非變數,當程式宣告乙個類,未申 請儲存空間,只有當這個類定義物件時才申請空間為了解決這個問題,c 編譯器提供了建構函式 constructor 來...