3

考虑以下代码:

class A
{
private:
    class B {};
public:
    B f();
};

A a;

A::B g()
{
    return a.f();
}

编译器拒绝这个 - g 不能返回 A::B 因为 A::B 是私有的。

但是假设我现在使用 decltype 来指定 g 的返回值:

class A
{
private:
    class B {};
public:
    B f();
};

A a;

decltype(a.f()) g()
{
    return a.f();
}

突然之间它编译得很好(使用 g++ >= 4.4)。

所以我基本上使用 decltype 来绕过访问说明符,这是我在 C++98 中无法做到的。

这是故意的吗?这是好习惯吗?

4

1 回答 1

5

访问仅适用于名称(作为特殊情况,适用于构造函数/析构函数)。它不适用于实体本身。规范进一步阐述

[ 注意:因为访问控制适用于名称,如果访问控制适用于 typedef 名称,则仅考虑 typedef 名称本身的可访问性。不考虑 typedef 引用的实体的可访问性。例如,

class A {
  class B { };
public:
  typedef B BB;
};

void f() {
  A::BB x; // OK, typedef name A::BB is public
  A::B y; // access error, A::B is private
}

——尾注]

所以你在这里发现的并不奇怪。A::B即使在 C++03 中,您也可以f通过说出地址&A::f并将其传递给推断返回类型的函数模板来获取类型。

于 2011-01-16T09:16:58.763 回答