0

为什么其中一些编译而一些不编译?

场景一:编译错误'main' : redefinition; previous definition was 'data variable'

#include <iostream>
using namespace std;
int main;
int main(){ }

场景二:编译错误syntax error : missing ';' before identifier 'obj

#include <iostream>
using namespace std;
class main { };
int main(){ 
   main obj;
} 

场景3:工作正常

#include <iostream>
using namespace std;
class main { };
int main(){ 
   class main obj;
} 

场景4:工作正常

#include <iostream>
using namespace std;
class main {};
main obj;
int main(){ }
4

1 回答 1

7

名称查找根据名称工作。查找该名称,与该名称指定的内容无关。

不允许在同一范围内将同名声明为函数和变量。

class X但是,即使X是函数名或变量名,也允许存在。当您拥有class X时,当前范围将X作为名称(指定该类)。如果同一作用域同时X声明为类型名和变量名,则只需查找即可x找到变量名。

如果声明了一个新的作用域X,那么在该作用域中的任何使用X都会找到在其作用域中声明的名称,这称为遮蔽。(名称查找搜索当前范围,然后搜索包含该范围的范围,依此类推,直到全局范围)。

  1. 错误,尝试同时声明main为函数和变量

  2. 要处理main obj;main查找名称。首先检查当前作用域,找到函数名main;所以它不检查全局范围。我们说内部作用域的名称遮蔽了外部作用域的名称。所以,这和你得到的错误是一样的void foo(); foo obj;

  3. class main明确地说要查找类名main;那没有找到int main(),所以它回退到检查全局范围。

  4. 没什么新鲜的,main obj;没什么区别。

另一个有趣的例子是:

int x;
class x { };

int main()
{
    x = 1;        // ok
    x y;          // error, `x` means the int
    class x y;    // ok
}
于 2014-09-22T05:17:46.110 回答