私有继承,return 引用基 class 的静态成员

Private inheritance, return reference to static member of base class

我有一个关于从 class 继承的简单问题,该 class 私下继承了基础 class,即我们有

class Base {};
class Heir: private Base {};
class HeirsHeir : public Heir {};

了解 HeirsHeir 无法访问 'its' Base 的任何内容。特别是,它不能有方法 returning 对自身的 Base & 引用。但为什么它不能 return 引用 另一个 Base 对象?那么为什么下面的代码不能编译:

class Base {};
class Kid : private Base {};
Base instance;
class Grandkid : public Kid
{
    const Base &GetInstance  () const
    { return instance; }
};

至少我的编译器(MinGW 5.3,即 Windows 的 gcc)给出了

error 'class Base Base::Base' is inaccessible at {}; 
error: within this context const Base &getInstance () const

根据我的理解,这没有意义,因为此时我没有调用 Base 的构造函数,而是 return 引用(对 Base 实例)。

请注意,可以使用

修复错误
const ::Base &GetInstance  () const
{ return instance; }

肯定链接到 C++03 §11.2/3(参见 [C++ private inheritance and static members/types

Note: A member of a private base class might be inaccessible as an inherited member name, but accessible directly.

但我不明白为什么这是必要的。有人可以解释一下吗?

我认为编译器无法识别 Base 是一个 class 名称,并且在您想要访问 Base 成员时识别它。

这也编译:

class Base {};
class Kid : private Base {};
Base instance;
class Grandkid : public Kid
{
    const class Base &GetInstance  () const
    { return instance; }
};

错误的用法是这样的:

class Base {
public:
    struct BaseStruct { int a; };
};
class Kid : private Base {
public:
    struct KidStruct { int a; };
};
Base instance;
class Grandkid : public Kid
{
    const class Base &GetInstance  () const
    { return instance; }

    const Kid::KidStruct kidStruct;
    const Base::BaseStruct baseStruct;
};

kidStruct没有错误,因为继承是public,但是baseStruct是不可访问的。

名称查找找到注入的-class-名称Base,它被注入Base(因此被GrandKid继承)。这是正确的,因为 injected-class-name 的范围比 class 的名称空间范围更近。但是,GrandKid 无法访问此注入的-class-名称,因为它在 Kid.

中是私有的

在编译器的错误消息中,Base::Base 没有引用构造函数,而是引用了注入到 Base 中的 class 名称 Base。请注意,当使用它的上下文强制将名称解释为类型时,您实际上可以合法地使用 Base::Base,就像在这个有效但 vile 代码中一样:

class Foo {};

std::vector<Foo::Foo::Foo::Foo> v;

[Live example]

然而,当使用 Base::Base 的上下文允许引用一个函数时,它被解析为构造函数而不是 class 名称(C++11 [ class.qual]3.4.3.1/2)