C ++歧义问题

时间:2015-11-12 13:11:14

标签: c++ inheritance ambiguous

请使用以下课程:

class BaseClass
{
    class OnSomeEventListener
    {
    public:
        enum SomeEnum { BLABLA }
        virtual void OnSomeEvent( SomeEnum eventData ) = 0;
    }
};

class ChildClass :
    public BaseClass,
    public BaseClass::OnSomeEventListener
{
    virtual void OnSomeEvent( BaseClass::OnSomeEventListener::SomeEnum eventData );
}

我的问题是:为什么我需要在BaseClass::方法的OnSomeEventListener::SomeEnum eventData前面指定virtual void OnSomeEvent( BaseClass::OnSomeEventListener::SomeEnum eventData );

如果我不这样做,则表示OnSomeEventListenerBaseClass::OnSomeEventListener之间的BaseClass::OnSomeEventListener::OnSomeEventListener不明确

为什么我认为我引用的是构造函数而不是OnSomeEventListener类型?为什么我需要在参数类型前加BaseClass::作为前缀,因为我已经在BaseClass内?

谢谢。

2 个答案:

答案 0 :(得分:4)

  

为什么我需要在BaseClass ::之前使用参数类型作为前缀?因为我已经在BaseClass中了?

你在BaseClass内,但你{em} 也在OnSomeEventListener内,因为你从两者继承。

当编译器解析一个名字时,它并不认为"我在这里需要一个类型,这可以是一个枚举吗?" ,而不是它认为"我在这里有一个名字,它可以是什么?" 。在您的情况下,它可以是两个不同的东西,具体取决于搜索名称的基类。

答案 1 :(得分:3)

你完全不需要BaseClass::OnSomeEventListener范围,因为你带有继承BaseClass::OnSomeEventListener

class ChildClass:
  public BaseClass,
  public BaseClass::OnSomeEventListener
{
  virtual void OnSomeEvent(SomeEnum eventData);
};

OnSomeEventListener中所说的ChildClass是不明确的,因为它可以是构造函数,也可以是该范围内的类,因为你继承了它们。

尝试使用名称OnSomeEventListener::SomeEnum时,其前面没有::,因此编译器使用unqualified lookup rules创建查找集 。从编译器错误中你可以看到它首先只考虑在该范围内直接变得模糊的OnSomeEventListener,因为类本身和构造函数都匹配。