C 虛析構函式和簡單的引用計數原理

2021-06-29 10:11:30 字數 2300 閱讀 5892

一直對c++虛析構函式和引用技術不是特別清楚,所以到網上搜了些資料,寫了乙個簡單的例子。

#include

class ******refbase

virtual ~******refbase()

void

lock()

void unlock()

private:

int mref_;

};class inheritedclass: public ******refbase

~inheritedclass()

};///

//////

//////

//////

//////

//////

int main()

//////

//////

//////

//////

//////

///

調出vs2005下的[visual studio 2005 命令提示]編譯檔案,編譯命令如下

cl hello.cpp

執行hello.exe結果如下:

func:******refbase::******refbase()mref_:1

func:inheritedclass::inheritedclass()

func:******refbase::unlock() mref_:0

func:inheritedclass::~inheritedclass()

func:******refbase::~******refbase()mref_:0

從log可以看出整個流程,基類構造→繼承類構造→引用計數減一後刪除自身→繼承類析構→基類析構,這是正常的流程。

※1但是,我如果將[virtual ~******refbase() ]前的virtual 去掉,執行結果如下:

func:******refbase::******refbase()mref_:1

func:inheritedclass::inheritedclass()

func:******refbase::unlock() mref_:0

func:******refbase::~******refbase()mref_:0

從log中可以看出,基類構造→繼承類構造→引用計數減一後刪除自身→[繼承類析構→]基類析構,沒有執行繼承類的析構。

※2對於引用計數,如果是區域性變數的話,不起作用。**修改如下:

int main()
執行結果:

func:******refbase::******refbase()mref_:1

func:inheritedclass::inheritedclass()

func:inheritedclass::~inheritedclass()

func:******refbase::~******refbase()mref_:1

引用計數還為1的情況下,兩個析構函式都走完了。

※3將基類的virtual去掉,並且main中還是用區域性變數

class ******refbase 

...};int main()

執行結果和※2的結果一樣,對於區域性變數來說,基類的虛析構函式加不加virtul都一樣,但對於基類指標指向繼承類這種情況,基類的虛析構函式很重要。

1.基類析構函式加virtul,主要是對於基類指標指向繼承類這種情況。對於區域性變數的話,不管有沒有基類虛析構函式,所有的析構函式都會被呼叫。

2.對於引用計數,也是對於new出來的物件。另外,當delete物件後(或者在將這塊記憶體還給系統之前),呼叫析構函式,而不是直接將這塊記憶體還給系統。

3.如果在類中加入virtual的話,會產生乙個虛函式表,會增加物件的空間,所以,如果這個類不作為基類的話,沒必要將析構函式寫成虛函式。

C 析構函式和虛析構函式。

析構函式如果不是虛的話,基類的析構函式將不會被呼叫。多型時,也就是派生類被基類指標所指,或者被基類別名 虛析構函式,被呼叫時,其自身的析構函式和基類的析構函式都將會被呼叫。非虛的時候,不進行多型,只有基類的會被呼叫。純虛析構函式 定義的時候除了加 0 還需要給出函式的實現。因為當遞迴的呼叫析構函式時...

C 虛析構函式和純虛析構函式

我們知道析構函式是在物件生命週期結束時自動被呼叫,用來做一些清理工作 如釋放控制代碼,釋放堆記憶體等 防止出現記憶體洩漏。那怎麼還有虛析構函式呢?使用虛析構函式的類一般是要作為基類,被其他類繼承。通過把基類的析構函式宣告為虛函式,就可以通過父類指標來釋放子類物件,從而完成子類的一些清理工作,防止出現...

c 的虛析構函式和純虛析構函式

虛函式是用作實現子類的多型性的,它可以在執行的過程中選擇子類或者父類的同名函式,意思就是說,每次只有乙個函式執行。但是對於析構函式來說,子類 與父類在銷毀物件時,都應該要呼叫 所以把父類的析構函式定義為虛函式,會發生什麼事情呢。class class b public a int main 可以發現...