程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> C++ >> C++入門知識 >> 透析C++類對象的內存模型

透析C++類對象的內存模型

編輯:C++入門知識

雖然有許多人對C++類對象表示懷疑,但在年復一年的不斷發展中,他的使用率也在不斷提高。如過要想對C++類對象充分了解,但前提是要深入理解到底什麼是C++類對象,及他是怎麼運作的。

首先介紹一下C++中有繼承關系的類對象內存的布局:在C++中,如果類中有虛函數,那麼它就會有一個虛函數表的指針__vfptr,在類對象最開始的內存數據中。之後是類中的成員變量的內存數據。

對於子類,最開始的內存數據記錄著父類對象的拷貝包括父類虛函數表指針和成員變量)。 之後是子類自己的成員變量數據。對於子類的子類,也是同樣的原理。但是無論繼承了多少個子類,對象中始終只有一個虛函數表指針。

為了探討C++類對象的內存布局,先來寫幾個類和函數首先寫一個基類:然後,我們多種不同的繼承情況來研究子類的內存對象結構。

1. 無虛函數集繼承

  1.  //子類1,無虛函數重載     
  2. class Child1 : public Base     
  3. {     
  4. public:     
  5. virtual void f1() { cout << "Child1::f1" << endl; }     
  6. virtual void g1() { cout << "Child1::g1" << endl; }     
  7. virtual void h1() { cout << "Child1::h1" << endl; }     
  8. int child1;     
  9. protected:     
  10. private:     
  11. };   

2. 有一個虛函數繼承

  1.  //子類1,無虛函數重載     
  2. class Child1 : public Base     
  3. {     
  4. public:     
  5. virtual void f1() { cout << "Child1::f1" << endl; }     
  6. virtual void g1() { cout << "Child1::g1" << endl; }     
  7. virtual void h1() { cout << "Child1::h1" << endl; }     
  8. int child1;     
  9. protected:     
  10. private:     
  11. };   

虛擬繼承的子類的內存結構,和普通繼承完全不同。虛擬繼承的子類,有單獨的虛函數表, 另外也單獨保存一份父類的虛函數表,兩部分之間用一個四個字節的0x00000000來作為分界。

子類的內存中,首先是自己的虛函數表,然後是子類的數據成員,然後是0x0,之後就是父類的虛函數表,之後是父類的數據成員。如果子類沒有自己的虛函數,那麼子類就不會有虛函數表,但是子類數據和父類數據之間,還是需要0x0來間隔。

因此,在虛擬繼承中,子C++類對象和父類的數據,是完全間隔的。存放子類自己的虛函數表和數據,中間以0x分界,最後保存父類的虛函數和數據。如果子類重載了父類的虛函數,那麼則將子類內存中父類虛函數表的相應函數替換。

  1. 簡介學習C++總結之談
  2. 對C++庫函數進行學習探索總結筆記
  3. C++類庫設計的基本構思與方法
  4. C++語言真的還有市場價值?
  5. C++類庫設計的基本構思與方法

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved