我认为c#语言编译器是一个独立的黑盒,能够理解特定语法的文本并生成编译后的代码。另一方面,. net框架是一个庞大的库,其中包含部分由c#和部分由c++编写的功能。所以。net框架依赖于c#语言,而不是反过来。
但是我不能把这个放进LINQ的工作方式。LINQ查询是c#编译器可以理解的特定语法文本。但是要建立自己的LINQ提供程序,我需要像IQueryable和IQueryProvider两者都在系统中定义的接口工作。框架的Linq命名空间。
这是否意味着c#语言提供的功能依赖于。net框架的一部分?c#语言知道。net框架吗?
。. NET框架包含许多部分。其中最重要的是CLR——公共语言运行时。所有。net语言都依赖于它,包括c#,因为它们产生的il代码不能被机器处理器执行。相反,CLR执行它。
还有基类库BCL,它可用于所有。net语言:c#, VB。. NET、Managed c++、f#、IronRuby,应有尽有。我怀疑它是不是用c#写的。它不依赖于这些语言的任何特性,因为类和OOP都是在CLR中构建的。
所以,是的,c#语言知道。net框架,它绝对必须知道它。考虑IEnumerable
:要将foreach
编译成GetEnumerator()
,并调用MoveNext()
, c#编译器必须知道IEnumerable
的存在。
或者想想属性!c#编译器知道Attribute
接口提供了哪些方法。
但是CLR本身并不了解c#。div。
LINQ查询是c#编译器可以理解的特定语法文本。
嗯,查询表达式是——但是编译器并不真正"理解"它们。它只是以一种非常机械的方式翻译它们。例如,使用以下查询:
var query = from foo in bar
where foo.X > 10
select foo.Y;
翻译成:
var query = bar.Where(foo => foo.X > 10)
.Select(foo => foo.Y);
编译器不知道任何关于Where
和Select
的含义。它们甚至不必是方法——如果你有合适的委托类型的字段或属性,编译器就会接受它。基本上,如果第二种形式可以编译,那么查询表达式也可以。
大多数LINQ提供者使用扩展方法来提供这些方法(Where
, Select
, SelectMany
等)。同样,它们只是c#语言的一部分——编译器并不知道或关心扩展方法做什么。
有关如何翻译查询表达式的详细信息,请参阅我的Edulinq博客系列的第41部分。您可能会发现我的Edulinq系列的其余部分也很有帮助——它基本上是一系列博客文章,其中我重新实现了LINQ to Objects,每次一个方法。这再次证明了c#编译器并不依赖于System.Linq
命名空间中的LINQ实现,或者类似的东西。