第一章 .NET体系结构(1)

117 阅读7分钟

1.1、C#与.NET的关系

  C#编译器专门用户.NET,这表示用C#编写的所有代码总是在.NET Framework中运行。对于C#语言来说,可以得出两个重要的结论:

  1. C#的结构和方法论反应了.NET基础方法论。
  2. 在许多情况下,C#的特定语言功能取决于.NET的功能,或依赖于.NET几类。

  C#是 一种相当新的编程语言,C#的重要性体现在以下两个方面:

  • 它是专门与Microsoft的.NET Framework一起使用而设计的(.NET Framework是一个功能非常丰富的平台,可开发、部署和执行分布式应用程序)。
  • 它是一种基于现代面向对象设计方法的语言,在设计它时,Microsoft还吸取了其他所有类似语言的经验,这些语言是近20年来面向对象规则得到广泛应用后才开发出来的。

  C#就其本身而言只是一种语言,尽管它是用来生成面向.NET环境的代码,但它本身不是.NET的一部分。.NET支持的一些特性,C#并不支持。而C#语言支持的另一些特性,.NET却不支持(如运算符重载)。

1.2 公共语言运行库

  .NET Framework的核心是其运行库执行环境,称为公共语言运行库(CLR) 或.NET运行库。通常将在CLR控制下运行的代码称为代码托管(managed code)
  但是,在CLR执行编写好的源代码(使用C#或其他语言编写的代码)之前,需要编译它们。在.NET中,编译分为两个阶段:

  1. 将源代码编译为Microsoft中间语言(IL)
  2. CLR把IL编译为平台专用的代码。 这个两阶段的编译过程非常重要,因为Microsoft中间语言是提供.NET的许多优点的关键。 Microsoft中间语言与Java字节码共享一种理念:它们都是低级语言,语法很简单(使用数字代码,而不是文本代码),可以非常快速地转换为本地机器码。对于代码,这种精心设计的通用语言有很重要的优点:平台无关性提高性能语言的互操作性

1.2.1 平台无关性

  首先,这意味着包含字节码指令的同一文件可以放在任意平台中,运行时编译过程的最后阶段可以很轻松地完成,这样代码就可以运行在特定的平台上。换言之,编译为中间语言就可以获得.NET平台无关性,这与编译为Java字节码就会得到Java平台无关性是一样的。
  注意.NET的平台无关性目前只是停留在理论范畴,.NET的完整实现只能用于Windows平台。

1.2.2 提高性能

  IL总是即时编译的(称为JIT编译),而Java字节码常常是解释性的。
  JIT编译器并不是把整个应用程序一次编译完(这样会有很长的启动时间),而是只编译它嗲用的那部分代码(这是其名称由来)。代码编译过一次后,得到的本地可执行程序就存储起来,直到退出该应用程序位置,这样在下次运行这部分代码时,就不需要重新编译了。Microsoft认为这个过程要比一开始就编译整个过程应用程序代码的效率要高得多,因为任何应用程序的大部分代码实际上并不是在每次运行期间都执行。使用JIT编译器,从来都不会编译这种代码。
  编译过程的最后一部分是在运行时进行的,JIT编译器确切地知道程序运行在什么类型的处理器上,可以利用该处理器提供的任何特性或特定的机器代码指令来优化最后的可执行代码。   传统的编译器会优化代码,但它们的优化过程是独立于运行代码的特定处理器的。这是因为传统的编译器是在发布软件之前编译为本地机器可执行的代码。即编译器不知道运行代码的处理器的类型。

1.2.3 语言的互操作性

  语言的互操作性,简而言之,就是能将任何一种语言编译为中间语言,编译为中间语言的代码可以从其他语言编译过来的代码进行交互操作。
1. Visio Basic 2012
2. Visio C++ 2012
  现在的C++源代码会继续编译为本地可执行代码,而不会有修改,但它独立于.NET运行库运行。如果让C++代码在.NET Framework中运行,就可以在代码的开头添加下述命令:

#using <mscorlib.dll>

  还可以把标记/dr传递给编译器,这样子编译器假定要编译托管代码,因此会生成中间语言,而不是本地代码。C++的一个有趣的问题是在编译成托管代码时,编译器可以生成包含内嵌本地可执行代码程序的IL。这表示在C++代码中可以把托管类型和非托管类型合并起来,因此托管C++代码:

class MyClass
{

  定义了一个普通的C++类,而代码:

ref class MyClass
{

  生成了一个托管类,就好像使用C#或Visio Basic 2012编写类一样。实际上,托管C++代码比C#代码更优越的一点是可以在托管C++代码中调用非托管C++类,而不必采用COM互操作功能。
  如果在托管类型上试图使用.NET不支持的特性(例如,模板或类的多集成),编译器就会出现一个错误,另外,在使用托管类时,还需要使用非标准C++功能。
  编写使用.NET的C++程序会得到几种不同的互操作场景。使用编译器设置/clr启用公共语言运行库支持时,就可以完全混合所有的本地和托管C++功能。其他选项(如/clr:safe和/clr:pure)可以限制C++指针的使用,从而像使用C#和Visio Basic那样编写完全的代码。
3. COM和COM+
  从技术上讲,COM和COM+并不是面向.NET的技术,因为基于它们的组件不能编译为IL(但如果原来的COM组件是用C++编写的,那么使用托管C++在某种程度上可以这么做)。但是,COM+仍然是一个重要工具,因为它包含一些.NET不具备的特性。另外,COM组件仍可以使用--.NET集成了COM的互操作性,从而使托管代码可以调用COM组件,COM组件也可以调用托管代码。一般情况下,把新组件编写为.NET组件,大多是为了方便,因为这样可以利用.NET基类和托管代码的其他优点。
4. Windows运行库
  Windows8中提供了一种新的运行库,可被新应用程序使用。这个运行库可在Visio Basic、C#、C++和JavaScript中使用。用在不同的环境中,它会发生相应的变化。例如,在C#中使用时,它看起来就像.NET Framework中的类;在JavaScript中使用时,它看起来就像JavaScript开发人员所惯用的JavaScript库;而在C++中使用时,它又像是一个C++标准库。这种多样性是通过使用语言投影实现的。