【问题标题】:Incomplete type in nested name specifier嵌套名称说明符中的类型不完整
【发布时间】:2014-07-28 12:07:50
【问题描述】:

我尝试在嵌套名称说明符中使用不完整类型,如下所示:

class A;

int b= A::c; // error: incomplete type ‘A’ used in nested name specifier

class A {
    static const int c=5;
};

在 N3797 工作草案的 3.4.3/1 中没有任何说明:

可以引用类或命名空间成员或枚举器的名称 在 :: 范围解析运算符 (5.1) 之后应用于 a 表示其类、命名空间或 枚举

那么行为实现是否依赖于?

【问题讨论】:

  • 您引用的部分并没有说您可以在类的前向声明之后使用嵌套名称。
  • @RSahu 名称 A 在使用之前已声明。这意味着这样的名称 using 与引用不矛盾。请注意,名称 A 是在使用之前声明的,如 3.4.1/4 中所述:A name used in global scope, outside of any function, class or user-declared namespace, shall be declared before its use in global scope.
  • 应该是A类{ public const int c = 5;};
  • 正式来说,这段代码格式不正确不是因为A不完整,而是因为c这个名字在使用的时候没有声明在A的范围内,所以限定名称查找 (3.4.3) 失败。我想编译器作者认为“类不完整”(因此,没有声明其成员,因此限定名称查找不可能成功)是一个更有帮助的错误消息。

标签: c++ language-lawyer


【解决方案1】:

简介

标准中有几个地方暗示你的代码格式不正确,但下面的引用不言自明:

3.3.2p6 声明点 [basic.scope.pdecl]

在类成员声明点之后,可以在其类的范围内查找成员名。

您的代码的问题不在于您试图进入不完整类型的主体内部,问题在于您只能在声明类成员名称之后引用它。

由于您的前向声明(当然)没有引入任何名为 c 的成员,因此引用此类名称是不正确的。


误导性诊断...

gccclang 在输入您的代码时发出的诊断有点误导,老实说,我觉得应该报告错误。

foo.cpp:3:8: error: incomplete type 'A' named in nested name specifier

我们允许在 nested-name-specifier 中命名不完整的类型,但如前所述;我们不允许引用尚未声明的成员。

格式错误:

class X {
  static int a[X::x];        // ill-formed, `X::x` has not yet been declared
  static int const x = 123;
};

法律:

class X {
  int const x = 123;
  int a[X::x]; // legal, `X` is incomplete (since we are still defining it)
               //        but we can still refer to a _declared_ member of it
};

【讨论】:

  • 错误的包含循环也可能导致此问题。检查您正在构建的错误类标头是否错误地包含在给您错误的类中。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-05-26
  • 2021-07-25
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多