含有虚函数,虚继承的类的大小

当类中含有虚继承时(在vs环境下,linux环境下有歧义)

1. 派生类对象中会添加一个指针,该指针指向虚继承的基类,称为虚类指针(cPtr)。每一个指针只指向其中一个虚继承的类,也就是说,虚继承了几个类,就会有几个cPtr。

    2. 父类当中的成员变量、虚函数指针(vPtr)、虚类指针(cPtr)仍然会被复制到派生类当中。但在不同继承模式下,vPtr和cPtr的效果是不同的。

        vPtr:普通继承时,子类当中如果有虚函数,会直接在父类的虚函数表中添加或者替换相应的选项;虚继承时,vPtr指向的基类虚表不可以再增加了;如果在派生类添加虚函数,分为三种情况:

          情况一:虚函数名称与父类当中的某个虚函数名相同,且派生类含有构造函数,会在结构体中产生一个和虚基类有关的vtordisp指针,该指针作用暂未知。

          情况二:虚函数名称与父类当中的某个虚函数名相同,且派生类不含构造函数,会直接修改基类虚函数表,类大小不变。

          情况三:虚函数名称与父类当中的任何一个虚函数都不同,需要重新添加一个vPtr,重新产生一个虚函数表,大小就会增加。

        cPtr:假设子类D同时继承了父类B和父类C,两个父类都虚继承了类A(A是无任何虚继承的类),根据子类D对B、C继承方式的不同,其cPtr的个数也是不同的

          (1). 父类B、C都是普通继承。这种情况下有两个cPtr,分别是从父类B和父类C中继承过来的,且指向虚继承的A。

          (2). 父类C是虚继承,B是普通继承时(或相反情况)。普通继承父类B时已经继承过A(有了一个cPtr),因此在虚继承父类C时,父类C虚继承的类A就不会再次继承,因此不会有第二个cPtr指向A。虚继承父类C也会产生一个cPtr。因此,此种情况下有两个cPtr。

          (3). 父类B、C都是虚继承。此时指向类A的cPtr仍然只有一个,另外有两个cPtr指向父类B、C,所以一共有三个cPtr。

猜你喜欢

转载自blog.csdn.net/cb673335723/article/details/81358928