为什么我可以创build一个名为“var”的类?
是不是在C#中的关键字? 但为什么我可以这样做:
public class var { } public class main { public static void main(string[] args) { var testVar = new var(); } }
代码中使用的var
是在main
类之前声明的var
类。 而编译器甚至不抱怨。
当我这样做的时候:
public class int { }
或这个:
public class true { }
编译器说int
或者是一个关键字,不能像那样使用。 为什么与var
不一样?
var
不是根据这个列表的关键字。
它是一个上下文关键字,所以从上下文来看,编译器能够决定哪个是你的类,哪个是上下文关键字,不会出现混淆。
一个上下文关键字是:
用于提供代码中的特定含义,但不是C#中的保留字。
所以它不保留,你可以使用它。
正如在上面的评论中指出的那样,在Eric Lipperts博客上讨论了这些差异以及在每个c#版本中添加的各种关键字和上下文关键字的列表
有趣的是,由于关键字集是在C#1.0中决定的,因此没有增加,以保持向后兼容性。
编译器足够聪明,知道你使用var
作为类名的上下文永远不是关键字的上下文,所以允许它(这就是为什么它被定义为上下文关键字 )。
另一种看待这个问题的方法是:“var”作为关键字不在C#的第一个版本中(不像“int”和“true”),所以你可能写了一些代码,然后有一个名为“var”的类。 这非常好,合法。 然后,当“var”被添加到语言中时,devise师们只是在特定的上下文中将其设置为关键字,所以现有的var类仍然可以工作。
这是语言devise的真正挑战之一 – 如何在不破坏现有代码的情况下添加新function,以及如何在不使新function使用起来变得麻烦的情况下。
在版本3之前的C#版本中, 隐式types的局部variables还不被支持,所以var
没有特别的意义,可以定义名为var
variables和类。 你的例子程序是合法的,因为这两个var
的main
引用var
类。
C#3及更高版本向下兼容,因此在版本3之前用C#编写的代码仍然与新编译器一起编译。
int
和true
是自C#1以来的关键字。
关键字可以在上下文中保留。 当源代码被parsing时,该上下文被build立为parsing树的一部分。 关键字的评估发生在这种情况下。 所以,在这种情况下,var不在保留的上下文中,并且与赋值语句中使用var的含义不同。 我相信这种灵活性的一个原因是,在C#3中引入了var,所以在任何地方保留var可能会破坏一些程序的向后兼容性,而将它用作variablestypes声明不会在早期版本中编译,所以没有破损。