本文共 2608 字,大约阅读时间需要 8 分钟。
先看下代码:
struct A{ A(int v=100):X(v){}; virtual void foo(void){} int X;}; struct B :virtual public A{ B(int v=10):Y(v),A(100){}; virtual void fooB(void){} int Y;}; struct C : virtual public A{ C(int v=20):Z(v),A(100){} virtual void fooC(void){} int Z;}; struct D : public B, public C{ D(int v =40):B(10),C(20),A(100),L(v){} virtual void fooD(void){} int L;}; int _tmain(int argc, _TCHAR* argv[]){ A a; int *ptr; ptr = (int*)&a; cout << ptr << " sizeof = " << sizeof(a) <
如果B虚拟继承A,则B的对象中要增加一个虚拟基类指针,其指向的表的第二项,即从本指针到虚拟基类的偏移。
例如,对象b,的虚拟基类的地址是120+8 = 128
虚拟基类在b对象的最后。
多重继承,继承n个类,有n个续表指针;包括n个虚基类,有n个虚基类指针。
举个例子,
B虚继承A,如果A中有虚函数,则B类对象的开始位置是虚表指针,第二个位置是虚基类的指针。
class A{public: A():a(1){} int a;};class B: public virtual A{public: B():b(2){} int b;};int main() { B* b = new B; A* a = dynamic_cast (b); if(a == b)//b先默认转为A*,所以相等 { std::cout << "equal" << std::endl; } else { std::cout << "not equal" << std::endl; }//输出equal if (int(b) == int(a)) { std::cout << "equal" << std::endl; } else { std::cout << "not equal" << std::endl; }//输出not equal typedef void (*pFun)(void); int **ptb = (int **)b; cout<output:<<" "< < <
equal
not equal 0 8 00701E5C 00701E60 ------- 00701E60 00701E58对象b的内存分布是:
虚基类的地址是 58+8 = 60
a为什么不等于b?
a指向了60的地址,而b指向的还是58
如果在虚继承的继承上又有多态重载?
class A{public: virtual void fun1() { cout<<"A"<(b); if(a == b) { std::cout << "equal" << std::endl; } else { std::cout << "not equal" << std::endl; }//输出equal if (int(b) == int(a)) { std::cout << "equal" << std::endl; } else { std::cout << "not equal" << std::endl; }//输出not equal cout< <
output:
equal
not equal 24 first vtb B:fun2 -4 12 2 0 second vtb B:fun1 1 ------- 00360A18 00360A0808 vftable ---->B:fun2()
0c base_psb---->-4,12
10 B:b
14 0//不知道为什么为0?
18 vftable------>B:fun1()
1c A:a
如果B类变为
class B: virtual public A
{ public: B():b(2){} virtual void fun1() { cout<<"B:fun1"<<endl; } void fun2() { cout<<"B:fun2"<<endl; } int b; };fun2不是虚函数,所以对象b的开始不是虚函数表指针,而是虚基类指针
pFun pfun;
cout<<ptb[0][0]<<" "<<ptb[0][1]<<endl; cout<<((int*)ptb)[1]<<endl;//B:b pfun =(pFun) ptb[3][0]; pfun(); /*cout<<(int)ptb[3]<<endl; pfun = (pFun)ptb[4][0]; cout<<"second vtb"<<endl; pfun();*/ cout<<((int*)ptb)[4]<<endl;//A:a cout<<"-------"<<endl; cout<<a<<endl<<b<<endl;output:
equal
not equal 20 0 12 2 B:fun1 1 ------- 004D3DB4 004D3DA8同样,为什么第2项为0?
转载地址:http://ipeti.baihongyu.com/