代碼如下:
#include<iostream>
using namespace std;
class Base {
public:
void fun(){cout<<"Base::fun"<<endl;}
virtual void f() { cout << "Base::f" << endl; }
virtual void g() { cout << "Base::g" << endl; }
virtual void h() { cout << "Base::h" << endl; }
int a;
int b;
};
class Base2:virtual public Base
{
public:
virtual void fun2(){cout<<"Base2::fun2"<<endl;}
virtual void f() { cout << "Base2::f" << endl; }
virtual void g() { cout << "Base2::g" << endl; }
virtual void h() { cout << "Base2::h" << endl; }
int a;
int b;
};
class Base3:virtual public Base
{
public:
virtual void fun3(){cout<<"Base3::fun3"<<endl;}
virtual void f() { cout << "Base3::f" << endl; }
virtual void g() { cout << "Base3::g" << endl; }
virtual void h() { cout << "Base3::h" << endl; }
int a;
int b;
};
class Derive: public Base2,public Base3
{
public:
//注意:如果Base2和Base3都是從Base繼承,且都重寫了Base的函數f,則Derive類必須要重寫函數f,否則
//在調用的時候會引起歧義,導致出錯。因此這樣編譯時不通過的。
virtual void f() { cout << "Derive::f1" << endl; }
virtual void g() { cout << "Derive::g1" << endl; }
virtual void h() { cout << "Derive::h1" << endl; }
virtual void fun(){ cout << "Derive::fun" << endl; }
int c;
int d;
};
int main()
{
typedef void(*Fun)(void);
Fun pFun = NULL;
Derive b;
cout<<"&b.Base::a="<<&b.Base::a<<endl;
cout<<"&b.Base::b="<<&b.Base::b<<endl;
cout<<"&b.c="<<&b.c<<endl;
cout<<"&b.d="<<&b.d<<endl;
cout<<"&b.Base2::a="<<&b.Base2::a<<endl;
cout<<"&b.Base2::b="<<&b.Base2::b<<endl;
cout<<"&b.Base3::a="<<&b.Base3::a<<endl;
cout<<"&b.Base3::b="<<&b.Base3::b<<endl;
cout << "Base2的虛函數表地址:" << (&b) << endl;
cout << "Base2的虛函數表 — 第一個函數地址:" << *(int*)(&b) << endl;
cout << "Base2的虛基類地址:" << *((int*)(&b)+1) << endl;
cout<<sizeof(b)<<endl;
pFun=(Fun)*((int*)*(int*)(&b));//Base2的虛函數
pFun();
pFun=(Fun)*((int*)*(int*)(&b)+1);//Derive的虛函數,注意Derive虛函數是在Base2的虛函數後面,
//兩者共享一個虛函數指針,如果Base2沒有除了基類以外的虛函數
//那這個指針就只有Derive的虛函數,如果Derive也沒有除了基類
//以外的虛函數,就不存在這個虛函數指針了
pFun();
pFun=(Fun)*((int*)*((int*)&b+4));//Base3的虛函數,同上面一樣,如果Base3中除了基類的虛函數外沒有其他
//虛函數,則不存在這個虛函數指針,所有的虛函數都到虛基類中的虛函數
//去尋找和執行
pFun();
cout<<*((int*)(&b)+1)<<endl;//Base2的虛基類指針
cout<<*((int*)(&b)+5)<<endl;//Base3的虛基類指針
cout<<*((int*)*((int*)&b+1)+1)<<endl;//虛基類距離當前Base2的偏移量,單位是字節
cout<<*((int*)*((int*)&b+5)+1)<<endl;//虛基類距離當前Base3的偏移量,單位是字節
system("pause");
return 0;
}
運行結果如下所示:
內存分佈如下所示: