c++中的虛析構函式到底什麼時候有用的,什麼作用呢。
一.虛析構函式的作用
總的來說虛析構函式是為了避免記憶體洩露,而且是當子類中會有指標成員變數時才會使用得到的。也就說虛析構函式使得在刪除指向子類物件的基類指標時可以呼叫子類的析構函式達到釋放子類中堆記憶體的目的,而防止記憶體洩露的.
我們知道,用c++開發的時候,用來做基類的類的析構函式一般都是虛函式。可是,為什麼要這樣做呢?下面用乙個小例子來說明:
但是,如果把類clxbase析構函式前的virtual去掉,那輸出結果就是下面的樣子了:
沒有調動子類的析構函式
也就是說,類clxderived的析構函式根本沒有被呼叫!一般情況下類的析構函式裡面都是釋放記憶體資源,而析構函式不被呼叫的話就會造成記憶體洩漏。我想所有的c++程式設計師都知道這樣的危險性。當然,如果在析構函式中做了其他工作的話,那你的所有努力也都是白費力氣。
所以,文章開頭的那個問題的答案就是--這樣做是為了當用乙個基類的指標刪除乙個派生類的物件時,派生類的析構函式會被呼叫。
當然,並不是要把所有類的析構函式都寫成虛函式。因為當類裡面有虛函式的時候,編譯器會給類新增乙個虛函式表,裡面來存放虛函式指標,這樣就會增加類的儲存空間。所以,只有當乙個類被用來作為基類的時候,才把析構函式寫成虛函式。
總結一下虛析構函式的作用:
(1)如果父類的析構函式不加virtual關鍵字
當父類的析構函式不宣告成虛析構函式的時候,當子類繼承父類,父類的指標指向子類時,delete掉父類的指標,只調動父類的析構函式,而不調動子類的析構函式。
(2)如果父類的析構函式加virtual關鍵字
當父類的析構函式宣告成虛析構函式的時候,當子類繼承父類,父類的指標指向子類時,delete掉父類的指標,先調動子類的析構函式,再調動父類的析構函式。
二.虛析構函式的原理分析
#includeusing namespace std;
class base
{public:
base(){cout<
(1)先呼叫父類的建構函式,再呼叫子類的建構函式,
這裡有乙個問題:父類的建構函式/析構函式與子類的建構函式/析構函式會形成多型,但是當父類的建構函式/析構函式即使被宣告virtual,子類的構造/析構方法仍無法覆蓋父類的構造方法和析構方法。這是由於父類的建構函式和析構函式是子類無法繼承的,也就是說每乙個類都有自己獨有的建構函式和析構函式。
(2)而由於父類的析構函式為虛函式,所以子類會在所有屬性的前面形成虛表,而虛表內部儲存的就是父類的虛函式
(3)當delete父類的指標時,由於子類的析構函式與父類的析構函式構成多型,所以得先調動子類的析構函式;之所以再調動父類的析構函式,是因為delete的機制所引起的,delete 父類指標所指的空間,要呼叫父類的析構函式。
所以結果就是這樣
參考:[1]
C 虛析構函式 純虛析構函式
虛析構函式 析構函式的工作方式是 最底層的派生類 most derived class 的析構函式最先被呼叫,然後呼叫每乙個基類的析構函式。因為在c 中,當乙個派生類物件通過使用乙個基類指標刪除,而這個基類有乙個非虛的析構函式,則結果是未定義的。執行時比較有代表性的後果是物件的派生部分不會被銷毀。然...
C 虛析構函式 純虛析構函式
虛析構函式 析構函式的工作方式是 最底層的派生類 most derived class 的析構函式最先被呼叫,然後呼叫每乙個基類的析構函式。因為在c 中,當乙個派生類物件通過使用乙個基類指標刪除,而這個基類有乙個非虛的析構函式,則結果是未定義的。執行時比較有代表性的後果是物件的派生部分不會被銷毀。然...
C 虛析構函式 純虛析構函式
虛析構函式 析構函式的工作方式是 最底層的派生類 most derived class 的析構函式最先被呼叫,然後呼叫每乙個基類的析構函式。因為在c 中,當乙個派生類物件通過使用乙個基類指標刪除,而這個基類有乙個非虛的析構函式,則結果是未定義的。執行時比較有代表性的後果是物件的派生部分不會被銷毀。然...