求教一些关于虚函数的问题。
class A{public: virtual void fa() { cout << "A::f" << endl; };};
class B : public A{public: void fa() { cout << "B::f" << endl; };};
class C : public A{public: void fa() { cout << "C::f" << endl; }; virtual fc() { cout << "C::f" << endl; };};
#include <iostream>using namespace std;class A{public: virtual void fa() { cout << "A::f" << endl; }};// 定义一个函数指针类型typedef void (*fun)();// 获取一个对象中的虚函数指针fun getVirtualFunction(A* obj, unsigned long offset){ // 1. obj就是类A的对象地址,而vfptr总是在一个对象内存布局的最前面,因此obj其实也就是vfptr的开始; // 2. 在32-bit的操作系统中,地址空间也是32-bit的,我们知道long是4Bytes,因此(unsigned long*)obj就是vfptr // 指针(即包括obj及其后面3个Bytes的内容,unsigned long*从本质上说,就是限定包括obj及其后面3个Bytes的 // 内容作为vfptr指针); // 3. *(unsigned long*)obj,就是vfptr指针中的内容,其中前4Bytes也就是virtual table的起始地址; // 4. (unsigned long *)(*(unsigned long*)obj)取得virtual table的4Bytes地址,也就是虚函数表中第一项,它也 // 是一个指针,这个指针指向第一个虚函数的地址,也就是说该指针的内容为第一个虚函数的指针;如果offset = 1, // 那么(unsigned long *)(*(unsigned long*)obj) + offset就是虚函数表中第二项,它是一个指向第二个虚函数地 // 址的指针,依此类推; unsigned long* vtbl = (unsigned long *)(*(unsigned long*)obj) + offset; // 5. 承4,如果vtbl是虚函数表中第一项,那么*(vtbl)就是第一个虚函数的指针,通过(fun)转化成为一个无参数,返回 // 值类型为void的函数指针,以此类推。 fun p = (fun) *(vtbl); return p;}int main(int argc, char** argv){ A a1; A a2; cout << &a1 << endl; // a1的虚函数表的地址,其实也就是a1的this指针 cout << &a2 << endl; // a2的虚函数表的地址,其实也就是a2的this指针 cout << getVirtualFunction(&a1, 0) << endl; // 对象a1的虚函数fa的指针 cout << getVirtualFunction(&a2, 0) << endl; // 对象a2的虚函数fa的指针 return 0;}