C++ 中多继承情况下 怎么确定某个类型的方法,在虚函数表中的位置

C++ 中多继承情况下 如何确定某个类型的方法,在虚函数表中的位置?
本帖最后由 OSReact 于 2015-04-16 18:41:33 编辑
class
    InterfaceU1
{
public:
    virtual void func1() = 0;
}

class
    InterfaceU2
{
public:
    virtual void func2() = 0;
}

class
    Wrapper
{
public:
    virtual InterfaceU1* getInterface1() = 0;
    virtual InterfaceU2* getInterface2() = 0;
}

class
    Base : public Wrapper, public InterfaceU1, public InterfaceU2
{
public:
    virtual InterfaceU1* getInterface1()
    {
        return this;
    }
    virtual InterfaceU2* getInterface2()
    {

        return this;
    }
    virtual void func1()
    {
        printf("%s", "func1");
    }

    virtual void func2()
    {
        printf("%s", "func2");
    }
}

假设有如下代码:

Base* pBase = new Base();
pBase->getInterface1()->func1();

其实以上代码等于:

Base* pBase = new Base();
InterfaceU1* pInterface1 = pBase->getInterface1();
pInterface1->func1();



C++编译后,Base类的虚函数表如下:
 
vTable:Wrapper     |Base::getInterface1()|Base::getInterface2()|Base::func1()|Base::func2()|
vTable:InterfaceU1 |Base::func1()|
vTable:InterfaceU2 |Base::func2()|


如果单继承情况下 ((InterfaceU1*) pObj)->func1() 很好理解,只需要pObj的vptr[0]处的函数地址即可。
但是多继承情况下,返回的指针pObj 如果用 ((InterfaceU1*) pObj)->func1()  如果依旧使用vptr[0] 则完全错误。
C++是如何得到当前应该使用vptr[??]位置的函数地址呢?
C++会动态的根据this的当前类型修改所用的是哪张虚表吗?(或者说,存在这种动态的判断吗。编译器是否无法确定)

------解决思路----------------------
设有代码
    Base* pBase = new Base();
    pBase->getInterface1()->func1();
    
    InterfaceU1* pIf = ((InterfaceU1*)pBase);

你可以尝试用printf("%p %p", pBase, pIf);打印出它们的实际值,在大部分编译器的实现下,两个值不同

所以下次在C++里做这类转换时,请用static_cast<InterfaceU1*>来提醒自己,地址已经发生改变了