About multiple inheritance and ambiguity

女生的网名这么多〃 提交于 2019-12-10 23:39:45

问题


In the following example:

class A {
public:
    virtual void f() { cout << "a" << endl; }
    virtual void h() { cout << "A" << endl; }
};
class s1 : public A {
public:
    virtual void f() { cout << "s1" << endl; }
};
class s2 : public A {
public:
    virtual void h() { cout << "s2" << endl; }
};
class GS : public s1, public s2 {
public:
};
int main()
{
    s1 *q = new GS;
    q->h();//no problem

    GS a;
    a.h();//error

}

Why does a.h(); give an ambiguity error yet q->h(); doesn't?

Doesn't *q have an instance of GS which should cause the same ambiguity problem?


回答1:


Your use of multiple inheritance causes two instances of A to appear in GS. When you use S1 *q to access the GS instance, it follows the A instance associated with S1. Since S1 does not implement h(), the output of q->h() will be the implementation provided by A itself.

If you want q->h() to use the implementation provided by S2, then you need to create a diamond using virtual inheritance. Doing so will also remove the ambiguity when using a.h(), since virtual inheritance will cause only one instance of A to appear in GS.

class s1 : virtual public A {
public:
    virtual void f() { cout << "s1" << endl; }
};
class s2 : virtual public A {
public:
    virtual void h() { cout << "s2" << endl; }
};



回答2:


Name lookup is based on static type not dynamic type. (And it has to be, since it occurs at compile time not run time.)




回答3:


Because your pointer is of type s1 so the compiler knows to call h() (inherited from class A). Try using a pointer of type GS and you'll get an error for the pointer too. In the case of GS you are inheriting from s1 and s2, both classes inherit from A and thus, multiple(2) definitions of h() are found which is ambigious. This is the dreaded diamond.




回答4:


Ok, this is because when the compiler evaluates q->h(), q only has one function named 'h' in its scope since it is of type s1.

When the compiler evaluates a.h(), a has two functions named 'h' in its scope. The one from s1 and the one from s2.

The compiler doesn't know which one you wanted to use, so it throws an error.




回答5:


*q doesn't give an ambiguity error because its type is s1*. This means that the compiler will call s1::h, which is unambiguous.



来源:https://stackoverflow.com/questions/35095227/about-multiple-inheritance-and-ambiguity

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!