深度探索C++对象模型-Data语义学

Data Member布局

  • 同一个Access Section(private, public等)中,data member的顺序按照声明顺序排列,但是没有规定需要连续排序。同时编译器可能会安插一些内部的data member(比如vptr),用来支持整个对象模型。
  • 不同Access Section中,member的排列顺序由编译器决定。

Data Member存取

-X是空基类,需要安插一个char,使得class的两个objects在内存上拥有唯一的地址;
-Size(A) = 4(为了支持virtual base class而额外增加的指针) + 1(base class本身) + 3(Alignment对齐) = 8
-Size(C) = 4(A) + 4(B) + 1(X,虚拟继承被A/B所共享) + 3(对齐) = 12

class X {};    //空虚基类          sizeof(X) = 1
class A: public virtual X {};   //sizeof(A) = 8
class B: public virtual X {};   //sizeof(B) = 8
class C: public A, public B {}; //sizeof(C) = 12
  • Static Data Members
    -直接存放于Data Segment,拥有唯一实体,不存在于class object中;
    -如果两个class声明了同名static members,编译器会对class中static data member名字进行修饰,使其独一无二;
    -对static data member取址,得到该member数据类型指针;nonstatic data member取址将得到该member在类中偏移。

  • Nonstatic Data Members
    -对nonstatic data member的存取需要在class object起始地址加上该member的偏移。

class A {public: int x; int y;};
A a;
a.y = 0;  //&a.y = &a + &A::y

Data Member和继承

  • 只有继承没有多态
    -base class subobject会在derived class中保持原样。
    深度探索C++对象模型-Data语义学_第1张图片
  • 有多态
    在很多版本编译器中vptr放在class前端。
    对于单一继承,其base class 和derived class的object都是从相同的地址开始的,其差别只是在于derived object比较大。
    深度探索C++对象模型-Data语义学_第2张图片
  • 多重继承和虚拟继承

总结:多继承,单继承都不会导致访问时间的增加,但是虚拟基类由于使用间接访问技术,会导致访问时间的增加。

你可能感兴趣的:(C++,c++)