У меня есть простой объект, скомпилируйте и запустите под 64-битной Ubuntu1804 с g ++:
struct Base1{ int mi,mj,mk,mh;};
struct Base2{ int ni,nj,nk,nh;};
struct Child1:virtual Base1{virtual void f(){}};
struct Child2:virtual Base1{virtual void f(){}};
struct Derive1:Child1,Child2{};
struct Child3:virtual Base2{virtual void f(){}};
struct Child4:virtual Base2{virtual void f(){}};
struct Derive2:Child3,Child4{};
struct Final:Derive1,Derive2{};
int main(){
cout<<"C1="<<sizeof(Child1)<<endl;
cout<<"C2="<<sizeof(Child2)<<endl;
cout<<"C3="<<sizeof(Child3)<<endl;
cout<<"C4="<<sizeof(Child4)<<endl;
cout<<"D1="<<sizeof(Derive1)<<endl;
cout<<"D2="<<sizeof(Derive2)<<endl;
cout<<"F ="<<sizeof(Final)<<endl;
return 0;
}
Программа выводит:
$ g++ om.cpp -O2 && ./a.out
C1=24
C2=24
C3=24
C4=24
D1=32
D2=32
F =64
Я знаю, что sizeof (B1)16, и Child1-Child4 при добавлении виртуальной функции (vptr указывает на vtable) добавит дополнительный размер указателя, поэтому они имеют размер 24, без проблем.Но почему размер Derive1 / Derive2 равен 32?Объектная модель c ++ добавляет дополнительный указатель, верно?Но что на самом деле делает этот дополнительный указатель, и почему необходимо добавить этот дополнительный 8-байтовый указатель?Я не вижу здесь никакой необходимости.
Большое спасибо.