单继承与多继承中的虚函数表和虚函数指针

单继承与多继承中的虚函数表和虚函数指针

 

首先,我们了解一下何为单继承,何为多继承??

单继承:一个子类只有一个直接父类。

多继承:一个子类有两个或多个直接父类。

单继承中的虚函数表分析:

示例程序:

  1. #include <iostream> 
  2. using namespace std; 
  3.  
  4. typedef void(*FUNC)(); 
  5.  
  6. class Base 
  7. public
  8.     virtual void func1() 
  9.     { 
  10.         cout << "Base::func1()" << endl; 
  11.     } 
  12.     virtual void func2() 
  13.     { 
  14.         cout << "Base::func2()" << endl; 
  15.     } 
  16. private
  17.     int _b; 
  18. }; 
  19.  
  20. class Derive :public Base 
  21. public
  22.     virtual void func1() 
  23.     { 
  24.         cout << "Derive::func1()" << endl; 
  25.     } 
  26.     virtual void func3() 
  27.     { 
  28.         cout << "Derive::func3()" << endl; 
  29.     } 
  30.     virtual void func4() 
  31.     { 
  32.         cout << "Derive::func4()" << endl; 
  33.     } 
  34. private
  35.     int _d; 
  36. }; 
  37. void PrintVfptr(int* vptr) 
  38.     //打印虚函数表 
  39.     cout << "虚函数表: " << vptr << endl; 
  40.     for (int i = 0; vptr[i] != 0; ++i) 
  41.     { 
  42.         printf("第%d个虚函数:%p  >> ", i, vptr[i]); 
  43. FUNC f = (FUNC)(vptr[i]);
  44.         f(); 
  45.     } 
  46.  
  47. void Test() 
  48.     Base b; 
  49.     Derive d; 
  50.  
  51.     int* vptrBase = (int*)(*(int*)(&b)); 
  52.     int* vptrDeri = (int*)(*(int*)(&d)); 
  53.  
  54.     PrintVfptr(vptrBase); 
  55.     cout << endl; 
  56.     PrintVfptr(vptrDeri); 
  57.  
  58.  
  59. int main() 
  60.     Test(); 
  61.     system("pause"); 
  62.     return 0; 
#include <iostream>
using namespace std;

typedef void(*FUNC)();

class Base
{
public:
	virtual void func1()
	{
		cout << "Base::func1()" << endl;
	}
	virtual void func2()
	{
		cout << "Base::func2()" << endl;
	}
private:
	int _b;
};

class Derive :public Base
{
public:
	virtual void func1()
	{
		cout << "Derive::func1()" << endl;
	}
	virtual void func3()
	{
		cout << "Derive::func3()" << endl;
	}
	virtual void func4()
	{
		cout << "Derive::func4()" << endl;
	}
private:
	int _d;
};
void PrintVfptr(int* vptr)
	//打印虚函数表
{
	cout << "虚函数表: " << vptr << endl;
	for (int i = 0; vptr[i] != 0; ++i)
	{
		printf("第%d个虚函数:%p  >> ", i, vptr[i]);
		FUNC f = (FUNC)(vptr[i]);
		f();
	}
}

void Test()
{
	Base b;
	Derive d;

	int* vptrBase = (int*)(*(int*)(&b));
	int* vptrDeri = (int*)(*(int*)(&d));

	PrintVfptr(vptrBase);
	cout << endl;
	PrintVfptr(vptrDeri);

}

int main()
{
	Test();
	system("pause");
	return 0;
}

程序运行结果:

Base类(基类)的虚函数表:

wKioL1bcEMbyJxs-AAAQf1oQ-Ns235.png

Derive类(派生类)的虚函数表:

wKiom1bcEHuxOB0QAAAcF7C983I617.png

结论:

如果有虚函数表,那么只有一个虚函数表,并且按照虚函数声明的顺序顺序排列,派生类的虚函数紧接着基类的虚函数排列


多继承中的虚函数表分析:

示例代码:

  1. #include <iostream> 
  2. using namespace std; 
  3.  
  4. typedef void(*FUNC)(); 
  5. class Base 
  6. public
  7.     virtual void func1() = 0; 
  8.     virtual void func2() = 0; 
  9. }; 
  10.  
  11. class Base1:public Base 
  12. public
  13.     virtual void func1() 
  14.     { 
  15.         cout << "Base1::func1()" << endl; 
  16.     } 
  17.     virtual void func2() 
  18.     { 
  19.         cout << "Base1::func2()" << endl; 
  20.     } 
  21. private
  22.     int _b1; 
  23. }; 
  24.  
  25. class Base2: public Base 
  26. public
  27.     virtual void func1() 
  28.     { 
  29.         cout << "Base2::func1()" << endl; 
  30.     } 
  31.     virtual void func2() 
  32.     { 
  33.         cout << "Base2::func2()" << endl; 
  34.     } 
  35. private
  36.     int _b2; 
  37. }; 
  38.  
  39.  
  40. class Derive : public Base1, public Base2 
  41. public
  42.     virtual void func1() 
  43.     { 
  44.         cout << "Derive::func1()" << endl; 
  45.     } 
  46.     virtual void func3() 
  47.     { 
  48.         cout << "Derive::func3()" << endl; 
  49.     } 
  50.     virtual void func4() 
  51.     { 
  52.         cout << "Derive::func4()" << endl; 
  53.     } 
  54. private
  55.     int _d; 
  56. }; 
  57.  
  58. void PrintVfptr(Base* b) 
  59.     int* vTable1 = (int*)(*(int*)b); 
  60.     cout << "虚函数表指针:" << vTable1 << endl; 
  61.     for (int i = 0; vTable1[i] != 0; ++i) 
  62.     { 
  63.         printf("第%d个虚函数指针: %p   >>", i, vTable1[i]); 
  64.         FUNC f = (FUNC)vTable1[i]; 
  65.         f(); 
  66.     } 
  67.     //int* vTable2 = (int*)(*((int*)b + sizeof(Base1) / 4)); 
  68.     int* vTable2 = (int*)(*((int*)((char*)b + sizeof(Base1)))); 
  69.     cout << "虚函数表指针:" << vTable2 << endl; 
  70.     for (int i = 0; vTable2[i] != 0; ++i) 
  71.     { 
  72.         printf("第%d个虚函数指针: %p   >>", i, vTable2[i]); 
  73.         FUNC f = (FUNC)vTable2[i]; 
  74.         f(); 
  75.     } 
  76.  
  77. void Test() 
  78.     Base1 b1; 
  79.     Base2 b2; 
  80.     Derive d; 
  81.     PrintVfptr(&b1); 
  82.     cout << endl; 
  83.     PrintVfptr(&b2); 
  84.     cout << endl; 
  85.     PrintVfptr((Base1*)&d); 
  86.  
  87. int main() 
  88.     Test(); 
  89.     system("pause"); 
  90.     return 0; 
#include <iostream>
using namespace std;

typedef void(*FUNC)();
class Base
{
public:
	virtual void func1() = 0;
	virtual void func2() = 0;
};

class Base1:public Base
{
public:
	virtual void func1()
	{
		cout << "Base1::func1()" << endl;
	}
	virtual void func2()
	{
		cout << "Base1::func2()" << endl;
	}
private:
	int _b1;
};

class Base2: public Base
{
public:
	virtual void func1()
	{
		cout << "Base2::func1()" << endl;
	}
	virtual void func2()
	{
		cout << "Base2::func2()" << endl;
	}
private:
	int _b2;
};


class Derive : public Base1, public Base2
{
public:
	virtual void func1()
	{
		cout << "Derive::func1()" << endl;
	}
	virtual void func3()
	{
		cout << "Derive::func3()" << endl;
	}
	virtual void func4()
	{
		cout << "Derive::func4()" << endl;
	}
private:
	int _d;
};

void PrintVfptr(Base* b)
{
	int* vTable1 = (int*)(*(int*)b);
	cout << "虚函数表指针:" << vTable1 << endl;
	for (int i = 0; vTable1[i] != 0; ++i)
	{
		printf("第%d个虚函数指针: %p   >>", i, vTable1[i]);
		FUNC f = (FUNC)vTable1[i];
		f();
	}
	//int* vTable2 = (int*)(*((int*)b + sizeof(Base1) / 4));
	int* vTable2 = (int*)(*((int*)((char*)b + sizeof(Base1))));
	cout << "虚函数表指针:" << vTable2 << endl;
	for (int i = 0; vTable2[i] != 0; ++i)
	{
		printf("第%d个虚函数指针: %p   >>", i, vTable2[i]);
		FUNC f = (FUNC)vTable2[i];
		f();
	}
}

void Test()
{
	Base1 b1;
	Base2 b2;
	Derive d;
	PrintVfptr(&b1);
	cout << endl;
	PrintVfptr(&b2);
	cout << endl;
	PrintVfptr((Base1*)&d);
}

int main()
{
	Test();
	system("pause");
	return 0;
}

程序运行结果:

Base1的虚函数表:

wKioL1bcFcSzAXRSAAAX-leGeyg336.png

Base2的虚函数表:

wKioL1bcFq2xTaMeAAAQJsD_jQU490.png

Derive的虚函数表:(有两个虚函数表)

wKioL1bcFyCAR3u_AAAq7ZbMpMs067.png

多继承中的菱形继承:

示例代码:

  1. #include <iostream> 
  2. using namespace std; 
  3.  
  4. typedef void(*FUNC)(); 
  5. class Base 
  6. public
  7.     virtual void func1() 
  8.     { 
  9.         cout << "Base::func1()" << endl; 
  10.     } 
  11.     virtual void func2() 
  12.     { 
  13.         cout << "Base::func2()" << endl; 
  14.     } 
  15. private
  16.     int _b; 
  17. }; 
  18.  
  19. class Parent1 :public Base 
  20. public
  21.     virtual void func1() 
  22.     { 
  23.         cout << "Parent1::func1()" << endl; 
  24.     } 
  25.     virtual void func3() 
  26.     { 
  27.         cout << "Parent1::func3()" << endl; 
  28.     } 
  29.     virtual void func4() 
  30.     { 
  31.         cout << "Parent1::func4()" << endl; 
  32.     } 
  33.     virtual void func5() 
  34.     { 
  35.         cout << "Parent1::func5()" << endl; 
  36.     } 
  37. private
  38.     int _p1; 
  39. }; 
  40.  
  41. class Parent2 :public Base 
  42. public
  43.     virtual void func1() 
  44.     { 
  45.         cout << "Parent2::func1()" << endl; 
  46.     } 
  47.     virtual void func3() 
  48.     { 
  49.         cout << "Parent2::func3()" << endl; 
  50.     } 
  51.     virtual void func6() 
  52.     { 
  53.         cout << "Parent2::func6()" << endl; 
  54.     }    
  55.     virtual void func7() 
  56.     { 
  57.         cout << "Parent2::func7()" << endl; 
  58.     } 
  59. private
  60.     int _p2; 
  61. }; 
  62.  
  63. class Child :public Parent1, public Parent2 
  64. public
  65.     virtual void func1() 
  66.     { 
  67.         cout << "Child::func1()" << endl; 
  68.     } 
  69.     virtual void func3() 
  70.     { 
  71.         cout << "Child::func3()" << endl; 
  72.     } 
  73.     virtual void func4() 
  74.     { 
  75.         cout << "Child::func4()" << endl; 
  76.     } 
  77.     virtual void func6() 
  78.     { 
  79.         cout << "Child::func6()" << endl; 
  80.     }    
  81.     virtual void func8() 
  82.     { 
  83.         cout << "Child::func8()" << endl; 
  84.     } 
  85. private
  86.     int _c; 
  87. }; 
  88.  
  89. void PrintVfptr(int* vptr) 
  90.     //打印虚函数表 
  91.     cout << "虚函数表: " << vptr << endl; 
  92.     for (int i = 0; vptr[i] != 0; ++i) 
  93.     { 
  94.         printf("第%d个虚函数:%p  >> ", i, vptr[i]); 
  95.         FUNC f = (FUNC)(vptr[i]); 
  96.         f(); 
  97.     } 
  98. void Test() 
  99.     Base b; 
  100.  
  101.     Parent1 p1;  
  102.     Parent2 p2; 
  103.  
  104.     Child c; 
  105.  
  106.     int* vptr_B = (int*)(*(((int*)(&b)))); 
  107.  
  108.     int* vptr_P1 = (int*)(*(((int*)(&p1)))); 
  109.  
  110.     int* vptr_P2= (int*)(*(((int*)(&p2)))); 
  111.  
  112.     PrintVfptr(vptr_B); 
  113.     cout << endl; 
  114.  
  115.     PrintVfptr(vptr_P1); 
  116.     cout << endl; 
  117.  
  118.     PrintVfptr(vptr_P2); 
  119.     cout << endl; 
  120.  
  121.     int* vptr_C_1 = (int*)(*(((int*)(&c)))); 
  122.     int* vptr_C_2 = (int*)(*(int*)((char*)(&c) + sizeof(Parent1))); 
  123.  
  124.     PrintVfptr(vptr_C_1); 
  125.     cout << endl; 
  126.     PrintVfptr(vptr_C_2); 
  127.     cout << endl; 
  128. int main() 
  129.     Test(); 
  130.     system("pause"); 
  131.     return 0; 
#include <iostream>
using namespace std;

typedef void(*FUNC)();
class Base
{
public:
	virtual void func1()
	{
		cout << "Base::func1()" << endl;
	}
	virtual void func2()
	{
		cout << "Base::func2()" << endl;
	}
private:
	int _b;
};

class Parent1 :public Base
{
public:
	virtual void func1()
	{
		cout << "Parent1::func1()" << endl;
	}
	virtual void func3()
	{
		cout << "Parent1::func3()" << endl;
	}
	virtual void func4()
	{
		cout << "Parent1::func4()" << endl;
	}
	virtual void func5()
	{
		cout << "Parent1::func5()" << endl;
	}
private:
	int _p1;
};

class Parent2 :public Base
{
public:
	virtual void func1()
	{
		cout << "Parent2::func1()" << endl;
	}
	virtual void func3()
	{
		cout << "Parent2::func3()" << endl;
	}
	virtual void func6()
	{
		cout << "Parent2::func6()" << endl;
	}	
	virtual void func7()
	{
		cout << "Parent2::func7()" << endl;
	}
private:
	int _p2;
};

class Child :public Parent1, public Parent2
{
public:
	virtual void func1()
	{
		cout << "Child::func1()" << endl;
	}
	virtual void func3()
	{
		cout << "Child::func3()" << endl;
	}
	virtual void func4()
	{
		cout << "Child::func4()" << endl;
	}
	virtual void func6()
	{
		cout << "Child::func6()" << endl;
	}	
	virtual void func8()
	{
		cout << "Child::func8()" << endl;
	}
private:
	int _c;
};

void PrintVfptr(int* vptr)
	//打印虚函数表
{
	cout << "虚函数表: " << vptr << endl;
	for (int i = 0; vptr[i] != 0; ++i)
	{
		printf("第%d个虚函数:%p  >> ", i, vptr[i]);
		FUNC f = (FUNC)(vptr[i]);
		f();
	}
}
void Test()
{
	Base b;

	Parent1 p1; 
	Parent2 p2;

	Child c;

	int* vptr_B = (int*)(*(((int*)(&b))));

	int* vptr_P1 = (int*)(*(((int*)(&p1))));

	int* vptr_P2= (int*)(*(((int*)(&p2))));

	PrintVfptr(vptr_B);
	cout << endl;

	PrintVfptr(vptr_P1);
	cout << endl;

	PrintVfptr(vptr_P2);
	cout << endl;

	int* vptr_C_1 = (int*)(*(((int*)(&c))));
	int* vptr_C_2 = (int*)(*(int*)((char*)(&c) + sizeof(Parent1)));

	PrintVfptr(vptr_C_1);
	cout << endl;
	PrintVfptr(vptr_C_2);
	cout << endl;
}
int main()
{
	Test();
	system("pause");
	return 0;
}

运行结果:

wKioL1bcGALwhph7AABvr4tJVO0897.png其中,Child有两个虚函数表,因为它有两个直接父类。


总结:多继承中会有多个虚函数表,几重继承就会有几个虚函数表。这些虚函数表会按照派生的顺序依次排列。如果子类改写了父类的虚函数,那么就会用子类自己的虚函数覆盖相应的父类虚函数;如果子类有新的虚函数,那么就添加到第一个虚函数表的末尾。

猜你喜欢

转载自blog.csdn.net/caogenwangbaoqiang/article/details/80082865
今日推荐