内存布局
- 默认32位编译下,4字节对齐
- 有虚函数情况下会在内存一开始多一个虚表指针
- 普通函数不占内存空间
- 静态成员不占内存空间
1. 通过cl命令输出hello.cpp中的类A的内存布局测试
# 输出指定类型的内存布局
cl hello.cpp /d1reportSingleClassLayoutA
# 输出所有类型的内存布局
cl hello.cpp /d1reportAllClassLayout
class A {
public:
char x;
int y;
bool z;
};
class A size(12):
+---
0 | x
| <alignment member> (size=3)
4 | y
8 | z
| <alignment member> (size=3)
+---
2. 虚函数/虚继承内存布局测试
class A {
public:
virtual void foo() = 0;
void bar() {};
char x;
int y;
bool z;
};
class B : public A {
public:
virtual void foo() override{};
void bar() {};
float b;
};
class C: virtual A {
public:
virtual void foo() override {};
void bar() {};
double c;
static bool c1;
};
class A size(16):
+---
0 | {vfptr}
4 | x
| <alignment member> (size=3)
8 | y
12 | z
| <alignment member> (size=3)
+---
A::$vftable@:
| &A_meta
| 0
0 | &A::foo
A::foo this adjustor: 0
class B size(20):
+---
0 | +--- (base class A)
0 | | {vfptr}
4 | | x
| | <alignment member> (size=3)
8 | | y
12 | | z
| | <alignment member> (size=3)
| +---
16 | b
+---
B::$vftable@:
| &B_meta
| 0
0 | &B::foo
B::foo this adjustor: 0
class C size(32):
+---
0 | {vbptr}
8 | c
+---
+--- (virtual base A)
16 | {vfptr}
20 | x
| <alignment member> (size=3)
24 | y
28 | z
| <alignment member> (size=3)
+---
C::$vbtable@:
0 | 0
1 | 16 (Cd(C+0)A)
C::$vftable@:
| -16
0 | &C::foo
3. 菱形继承内存布局测试
class A1 {
public:
int a;
};
class B1 : public A1 {
public:
int b;
};
class C1 : public A1 {
public:
int c;
};
class D1 : public B1, public C1 {
public:
int d;
};
class A1 size(4):
+---
0 | a
+---
class B1 size(8):
+---
0 | +--- (base class A1)
0 | | a
| +---
4 | b
+---
class C1 size(8):
+---
0 | +--- (base class A1)
0 | | a
| +---
4 | c
+---
class D1 size(20):
+---
0 | +--- (base class B1)
0 | | +--- (base class A1)
0 | | | a
| | +---
4 | | b
| +---
8 | +--- (base class C1)
8 | | +--- (base class A1)
8 | | | a
| | +---
12 | | c
| +---
16 | d
+---
4. 虚菱形继承测试
class A2 {
public:
int a;
};
class B2 : virtual public A2 {
public:
int b;
};
class C2 : virtual public A2 {
public:
int c;
};
class D2 : public B2, public C2 {
public:
int d;
};
class A2 size(4):
+---
0 | a
+---
class B2 size(12):
+---
0 | {vbptr}
4 | b
+---
+--- (virtual base A2)
8 | a
+---
B2::$vbtable@:
0 | 0
1 | 8 (B2d(B2+0)A2)
vbi: class offset o.vbptr o.vbte fVtorDisp
A2 8 0 4 0
class C2 size(12):
+---
0 | {vbptr}
4 | c
+---
+--- (virtual base A2)
8 | a
+---
C2::$vbtable@:
0 | 0
1 | 8 (C2d(C2+0)A2)
vbi: class offset o.vbptr o.vbte fVtorDisp
A2 8 0 4 0
class D2 size(24):
+---
0 | +--- (base class B2)
0 | | {vbptr}
4 | | b
| +---
8 | +--- (base class C2)
8 | | {vbptr}
12 | | c
| +---
16 | d
+---
+--- (virtual base A2)
20 | a
+---
D2::$vbtable@B2@:
0 | 0
1 | 20 (D2d(B2+0)A2)
D2::$vbtable@C2@:
0 | 0
1 | 12 (D2d(C2+0)A2)
vbi: class offset o.vbptr o.vbte fVtorDisp
A2 20 0 4 0
参考
https://www.cnblogs.com/zzqcn/p/4742295.html