memory layout for C + + objects (bottom) The class memory layout of " single virtual Inheritance " and " Diamond type Virtual inheritance " in this article is not very clear, I have a question, I use VS2005, so record.
The class inheritance diagram is as follows:
Here: Class B is inherited by the class B1 and B2, while B1 and B2 are both inherited by D.
B1 f (), B2 F ( ) covers the F () of B;
D's F () covers the B1 f (), and D's F1 () covers the B1 F1 ()
D's F () covers the B2 f (), and D's F2 () covers the B2 F2 ()
The class code is as follows:
Class b{Public:int IB; Char CB; Public:b (): IB (0), CB (' B ') {} virtual void F () {cout << "b::f ()" << Endl;} virtual void Bf () {cout << "B::BF ()" << Endl;}}; Class B1:virtual public b//virtual inheritance, Diamond Type inheritance {public:int ib1; Char CB1; PUBLIC:B1 (): IB1 (one), CB1 (' 1 ') {} virtual void F () {cout << "b1::f ()" << Endl;} virtual void F1 () {cout << "b1::f1 ()" << Endl;} virtual void Bf1 () {cout << "b1::bf1 ()" << Endl;}}; Class B2:virtual public b{public:int ib2; Char CB2; PUBLIC:B2 (): Ib2 (n), CB2 (' 2 ') {} virtual void F () {cout << "b2::f ()" << Endl;} virtual void F2 () {cout << "b2::f2 ()" << Endl;} virtual void Bf2 () {cout << "b2::bf2 ()" << Endl;} }; Class D:public B1, public b2{public:int ID; char cd; PUBLIC:D (): ID (+), CD (' D '{} virtual void F () {cout << "d::f ()" << Endl;} virtual void F1 () {cout << "d::f1 ()" << Endl;} virtual void F2 () {cout << "d::f2 ()" << Endl;} virtual void Df () {cout << D::D f () "<< Endl;}};
(1) Single virtual inheritance: B1 virtual inherit from B
The code for viewing the memory layout of class B1 is as follows:
{int** pvtab = NULL; Fun Pfun = NULL; B1 Bb1;pvtab = (int**) &bb1;cout << "sizeof (B1) =" << sizeof (B1) << endl;cout << "[0] B1::_vfp Tr-> "<< endl;for (int i = 0;; i++) {Pfun = (fun) pvtab[0][i];cout << ' \ t ' <<" ["<< I << "] 0x" << (int*) pfun << "\ t"; if (pfun = = NULL) {cout << endl;break;} Pfun ();} cout << "[1] b1::_vbptr->" << endl;cout << "\ t" << "[0] b1db1bptrb1" << pvtab[1][0] < < endl;cout << "\ t" << "[1] b1db1bptrb" << pvtab[1][1] << endl;cout << "[2] b1::ib1 =" << (int) pvtab[2] << endl;cout << "[3] B1::CB1 =" << (char) pvtab[3] << endl;cout << "[ 4] = 0x "<< (int*) pvtab[4]/*[0]*/<< endl;cout <<" [5] b::_vfptr-> "<< endl;//cout << ' \ t ' << ' [' << 0 << '] thunk = 0x "<< (int*) pvtab[5][0] << endl;for (int i = 1;; i++) {Pfun = (fun) pvtab[5][i];cOut << ' \ t ' << "[" << I << "] 0x" << (int*) pfun << "\ t"; if (pfun = = NULL) {cout << ; Endl;break;} Pfun ();} cout << "[6] B::ib =" << (int) pvtab[6] << endl;cout << "[7] B::ic =" << (char) pvtab[7] < ;< Endl;}
The code outputs the layout of the class B1:
sizeof (B1) =
[0] B1::_vfptr->
[0] 0x0041106e b1::f1 ()
[1] 0x004110af b1::bf1 ()
[2] 0x00000000
[1] b1::_vbptr->
[0] B1db1bptrb1-4
[1] B1DB1BPTRB 16
[2] b1::ib1 = 11
[3] B1::ic1 = 1
[4] = A null delimiter in the 0x00000000//vc++ separates the layout of B and B1
[5] b::_vfptr->
[0] 0x00411055 // Strange Place : This is not the address of the function b1::f (), because the function that executes this address has an error, so where is the b1::f () virtual function of the entire B1 class? Is it the address of the "adjustment block"?
[1] 0x004111f4 B::BF ()
[2] 0x00000000
[6] b::ib = 0
[7] b::ic = B
(2) Virtual inheritance of diamond type
The code for viewing the memory layout of class D is as follows:
{int** pvtab = NULL; Fun Pfun = null;d D;pvtab = (int**) &d;cout << "sizeof (d) =" << sizeof (d) << endl;cout << "[0] D::b1::_vfptr-> "<< endl;for (int i = 0;; i++) {Pfun = (fun) pvtab[0][i];cout << ' \ t ' <<" ["<< I << "] 0x" << (int*) pfun << "\ t"; if (pfun = = NULL) {cout << endl;break;} Pfun ();} cout << "[1] d::b1::_vbptr->" << endl;cout << "\ t" << "[0] ddb1bptrb1" << pvtab[1][0] &l t;< endl;cout << "\ t" << "[1] ddb1bptrb" << pvtab[1][1] << endl;cout << "[2] b1::ib1 =" << (int) pvtab[2] << endl;cout << "[3] B1::CB1 =" << (char) pvtab[3] << endl;cout << " [4] d::b2::_vfptr-> "<< endl;for (int i = 0;; i++) {Pfun = (fun) pvtab[4][i];cout << ' \ t ' <<" ["<& Lt I << "] 0x" << (int*) pfun << "\ t"; if (pfun = = NULL) {cout << endl;break;} Pfun ();} cout << "[5] D::B2::_VBPTR-≫ "<< endl;cout <<" \ t "<<" [0] ddb2bptrb2 "<< pvtab[5][0] << endl;cout <<" \ T "< < "[1] ddb1bptrb" << pvtab[5][1] << endl;cout << "[6] b2::ib2 =" << (int) pvtab[6] << en Dl;cout << "[7] b2::cb2 =" << (char) pvtab[7] << endl;cout << "[8] D::id =" << (int) pvtab[8 ] << endl;cout << "[9] d::cd =" << (char) pvtab[9] << endl;cout << "[Ten] = 0x" << (int *) pvtab[10]/*[0]*/<< endl;cout << "[One] d::b::_vfptr->" << endl;cout << ' \ t ' << "[" < < 0 << "] 0x" << (int*) pvtab[11][0] << endl;//Strange place for (int i = 1;; i++) {Pfun = (fun) Pvtab[11][i];co UT << ' t ' << "[" << I << "] 0x" << (int*) pfun << "\ t"; if (pfun = = NULL) {cout << Endl;break;} Pfun ();} cout << "[B::ib] =" << (int) pvtab[12] << endl;cout << "[] B::ic =" << (char) pvtab[13] << Endl;}
the code outputs the layout of Class D:
sizeof (D) =
[0] D::b1::_vfptr->
[0] 0x00411163 d::f1 ()
[1] 0x004110af b1::bf1 ()
[2] 0x004110d2 D::D f ()
[3] 0x00000000
[1] d::b1::_vbptr->
[0] Ddb1bptrb1-4
[1] DDB1BPTRB 40
[2] b1::ib1 = 11
[3] B1::CB1 = 1
[4] D::b2::_vfptr->
[0] 0x0041101e d::f2 ()
[1] 0x00411159 b2::bf2 ()
[2] 0x00000000
[5] D::b2::_vbptr->
[0] Ddb2bptrb2-4
[1] DDB1BPTRB 24
[6] B2::ib2 = 12
[7] b2::cb2 = 2
[8] d::id = 100
[9] d::cd = D
= a null delimiter in the 0x00000000//vc++ separates the layouts of B and B1 and B2
[one] d::b::_vfptr->
[0] 0x004110c3 // Strange Place : This is not the address of the function d::f (), because the function that executes this address will go wrong, then the whole class D:: F () Where is the virtual function? is it the address of the "adjustment block"?
[1] 0x004111f4 B::BF ()
[2] 0x00000000
[B::ib] = 0
[B::CB] = B
I don't know what's going on at the moment, but I'm not sure if it's thunk or something.
Reference the memory layout of the:c++ object (bottom)