Joã*_*nso 47 c++ declaration definition language-lawyer name-lookup
下面的代码片段编译(演示):
struct A{ int i = 10; };
int main() {
    struct A{ int i = 20; };
    struct A;
    struct A a;
}
Run Code Online (Sandbox Code Playgroud)
但这不是:
struct A{ int i = 10; };
int main() {
//    struct A{ int i = 20; };
    struct A;
    struct A a;
}
Run Code Online (Sandbox Code Playgroud)
我可以看到答案可能是标准中的这些段落:
[basic.lookup.elab]/2和[basic.scope.pdecl]/7.
但我真的不知道如何从这两段中推断出上面显示的不同行为.
需要注意的是在第一个例子中,struct A是不是第一次在声明阐述类型说明符 struct A;,但在定义struct A中main().
在第二个例子中,struct A也未先在声明阐述型说明符 struct A;,但在定义struct A在全局范围.
Okt*_*ist 67
每个示例都包含两个不同类的声明,两个类都带有名称A.
让我们通过将其中一个重命名为以下来区分类B:
struct A{ int i = 10; };
int main() {
    struct B{ int i = 20; };
    struct B;
    struct B b;
}
Run Code Online (Sandbox Code Playgroud)
以上内容与您的第一个示例在语义上相同.该课程A从未使用过.
struct A{ int i = 10; };
int main() {
    struct B;
    struct B b;
}
Run Code Online (Sandbox Code Playgroud)
这在语义上与第二个示例相同.您正在尝试创建一个不完整类型的对象,即前向声明的类B.
重命名B为A不会改变任何东西,因为A在main阴影中声明了另一个A在全局范围内的声明.
[basic.lookup.elab]/2
如果elaborated-type-specifier没有嵌套名称说明符,并且[...]如果elaborated-type-specifier出现在具有以下形式的声明中:
class-keyattribute-specifier-seq选择identifier;在阐述了式说明符是引入了一个声明类名如[basic.scope.pdecl]中描述.
这struct A;是一个声明,它在声明的范围内引入了类名.在任何情况下,它都不能引用在外部范围内声明的类.
[basic.scope.pdecl]/7
[ 注:其他形式的详细类型说明符不会声明新名称[...] - 尾注 ]
通过暗示,这种形式的详细类型说明符声明了一个新名称.
Fra*_*eux 44
在第二个示例中,该行struct A;是主函数范围中名为A的结构的前向声明.该结构将优先于全局struct A.下一行定义了一个名为atype 的变量struct A.由于a struct A是在main函数的范围内声明的,因此编译器将在那里搜索它的定义.它没有找到一个(它被注释掉了).第一个示例编译,因为在同一范围内有定义.但是,以下示例将编译,因为它指定A了全局命名空间中的:
struct A{ int i = 10; };
int main() {
//    struct A{ int i = 20; };
    struct A;
    struct ::A a;
}
Run Code Online (Sandbox Code Playgroud)
        小智 5
它不能编译,因为它找不到A的定义.
int main() {
//    struct A{ int i = 20; };
      struct A;
      struct A a;
}
Run Code Online (Sandbox Code Playgroud)
上面的代码等于你的第一个例子,因为全局A被本地A遮蔽.在第二个例子中,A没有定义.这只是一个原型.原型应该放在需要定义的代码之前,当定义放在需要它的代码之后.如果编译器找不到该定义,它将失败,因为它不知道A应该是什么(全局定义被本地原型遮蔽,这导致它被忽略).
|   归档时间:  |  
           
  |  
        
|   查看次数:  |  
           4188 次  |  
        
|   最近记录:  |