




版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
1、. NET框架什么是.NET框架?它包含了哪些内容?为开发程序提供了哪些支持?很多朋友对这类 个问题的第一反应可能是.NET框架所提供的庞大类库及编写代码所采用的C#语言,实际上 远不止这些。要描述.NET框架,自然会遇到与其相关的一系列专业的技术术语和缩写,相信大家已 经见到过许多了,比如:CLR CIL、CTS、CLS、CLR、JIT、BCL、FCL、Module Assembly 等, 足以让很多人一头雾水、望而却步。笔者不会像字典一样按首字母排序对术语进行逐一解释, 因为这样还是难以理解。我们还是从大家最熟悉的东西开始吧!1-1引子设想一下:编写下面这样一个最简单的显示“Hello,
2、World! ”的控制台程序,并将 该程序运行起来需要哪几个步骤呢?using System;class Program static void Main(string args) string text = hello, world!Console. WriteLine (text);)这些步骤包括:打开Visual Studio,创建一个C#控制台应用程序项目(在这里将它命名为ConsoleApp),编写代码,编译程序然后运行。虽然这样的程序谁都会写,但是再 多进行一下思考就会发现,尽管是一个很小的程序,但已经引入了.NET框架的几个重要方 面。q据美方案DotNetStudy,(3个项目
3、)/ 簟 ConsoleAppF司 Propertiesa引用 绘 app.config图 Program.cs图6-6删除掉所有的项目引用using System;using System. Collections. Generic;using System. Linq;using System. Text;namespace ConsoleApp classProgram (staticvoid Main(string args) string text = Hello, world!Console. WriteLine (text);可能有人会认为,在删掉这些引用之后,编译器将会毫不客气
4、地提示编译错误:未能 找到类型或命名空间“System(是否缺少using指令或程序集引用?)。可实际上,当编 译并运行上面的代码时,程序会正确无误地执行。这是因为我们已经删掉了所有引用的程序 集,只定义了一个Program类型,并没有定义Console类型,所以此时要面对的第一个问题 就是:Console类型从哪里来?Visual Studio提供了一个快捷的办法使我们可以快速查看类型:将光标定位在 Console 然后按下键盘上的F12,就可以看到Console的类型定义。在Console类型定 义的最上方,可以看到它所在的程序集地址:C:Program FilesReferenceAss
5、embliesMicrosoftFramework. NETFrameworkv4. 0mscorlib. dll。ftregion 程序集 mscorlib. dll, v4. 0. 30319/ C:Program FilesReferenceAssembliesMicrosoftFramework. NETFrameworkv4. 0mscorlib.dll ftendregionusing System. 10;using System. Runtime. ConstrainedExecution;using System. Security;using System. Text;na
6、mespace System public static class Console /中间略)可以看到Console类型来自于mscorlib. dll这个程序集。从上面的实验可以看出,不 管我们是否引用mscorlib. dll程序集,它总是会自动引用进来。这个程序集中所包含的类 库,即是本节标题中的BCL (Base Class Library,基类库)。从名字就可以看出来,这个 类库包含的都是些最基本的类型,其本身已经与CIL语言融为一提了,为CIL语言提供基础 的编程支持,以至于该类库已经成为了 CLI标准的一部分(后面会介绍,因此也可以说BCL 中的类型就是CIL语言的类型,所有面
7、向CIL的语言都能够使用它们。我们可以使用对象浏 览器(Visual Studio菜单一视图一对象浏览器)来查看mscorlib. dll程序集中都包含了 哪些命名空间和类型,如图6-7所示。对象浏览器X 浏览:我的解天方案/ -O mscorlibt ( Microsoft.Runtime.Hostingt ( Microsoft.Win320 Microsoft.Win32.SafeHandlest ( System ( System.Collections.Concurrentt ( System.Collections.Generic ( Sy ste m. D e p I oy m
8、e nt.I nte r n a I ( System.Diagnostics.ContractsD ( System.Diagnostics.Contracts.Internal System.Diagnostics.Eventingt ( System.Diagnostics.SymbolStore() System.Globalizationt ( System.IO( System.IO.IsolatedStorage -O mscorlib/,口 System0 ( Microsoft.CSharp0 ( Microsoft.VisualBasict ( Microsoft.Win3
9、20 ( Systemt ( System.CodeDom0 System.CodeDom.Compiler System.Collections.ConcurrentD ( System.Collections.Generic0 ( System.Collections.ObjectModelD* ( System.Configuration0 System.Diagnostics ( System.IO0 System.IO.Compression彳in图6 9 System, dll中包含的命名空间这又是怎么回事呢?实际上,只要点开System命名空间就会发现,mscorlib. dll
10、的 System命名空间下面定义的类型和System, dll的System命名空间下面定义的类型完全不 同,它们之间并没有冲突之处。现在就明白了:BCL提供了像Console这样的类型来支持开发者编写类似控制台这样的 程序。既然已经思考了这么多,不妨再深入一下,思考这样一个问题:写下的这条语句string text = hello, world !”,其中的 string 从哪里来?从直觉来看,string 在 Visual Studio 中以深蓝色呈现,属于C#的关键字,那么它应该是C#提供的内置类型。可是,当我们将光 标移动到string上并按下F12时,转到string的定义时,看到的
11、却是下面这样的内容:ftregion 程序集 mscorlib. dll, v4. 0. 30319/ C:Program FilesReferenceAssembliesMicrosoftFramework. NETFrameworkv4. 0mscorlib. dll #endregionusing System. Collections;using System. Collections. Generic;/为了节约篇幅,省略了一些usingnamespace System public sealed class String : IComparable, ICloneable, ICo
12、nvertible, IComparable, IEnumerable, lEnumerable, IEquatable /省略定义)注意最上方的程序集地址,再次看到了 mscorlib. dll,并且String类型与Console 类型一样,同位于System命名空间下。由此可见,C#的关键字string,不过是BCL中 System. String类型的一个别名而已。类似地,VB. NET中的String关键字也是BCL中的 System. String类型的别名。因此,在.NET框架中,语言从本质上来说没有太大的区别,更 多的区别是在语法方面。从上面的例子也可以看出,C#和VB.NET
13、的很多语言能力并不是自 己的,而是从CIL “借”过来的这样做也保证了在不同语言中相应类型的行为是一致的。表6-1列出了几个典型的,不同语言关键字与CIL类型的对应关系。笔者觉得理解重 于记忆,所以这里只列出了几个。要了解其他基础类型时,只要将光标移动到类型上,然后 再按下F12键就可以了。表6-1不同语言关键字与CIL类型的对应关系CIL类型C#关键字VB.NET关键字System. BytebyteByteSytem.Intl6shortShortSystem.Int64longLong从表6T可以看出,.NET同时也对语言开发者提供支持.如你需要设计一款语言,那么 在开发编译器时将语言的
14、关键字映射为CIL中的类型就可以了,也就是说,对自己语言中的 一些特殊符号(关键字)进行映射处理,就好像C#中的关键字int和string一样。大家可能听说过这样一种特殊的类型一一基元类型(Primitive Type) o实际上,讲到 这里大家应该已经明白了,那些由编译器直接支持,将语言本身的关键字类型转换为CIL 类型的,就叫做基元类型。显然,上面的byte、int、string都是基元类型。而C#中并没 有一个关键字去映射Console,所以我们认为Console只是普通的类类型(Class Type) o3. 2 FCL框架类库作为一名.NET程序员,每天都要打交道的就是FCL 了 (
15、Framework Class Library,框 架类库)。在上一节中介绍了 BCL,它是FCL的一个子集。BCL中包含了与编译器及CIL语 言关系紧密的核心类型,以及常见开发任务中都会使用到的类型。而FCL包含的内容极多, 仅服务于一种应用场景的子类库就足够写一本书了,这里仅简单对它进行介绍。从功能上来看,可以将FCL框架类库划分成以下几层。最内一层,由BCL的大部分组成,主要作用是对.NET框架、.NET运行时及CIL语言本身进行支持,例如基元类型、集合类型、线程处理、应用程序域、运行时、安全性、互操作等。中间一层,包含了对操作系统功能的封装,例如文件系统、网络连接、图形图像、XML操作
16、等。最外一层,包含各种类型的应用程序,例如Windows Forms Asp. NETWPF、WCF、WF 等。.4 CTS公共类型系统假设要开发一套新的语言,这种语言和C#或VB.NET一样,在编译后也能够生成CIL 代码,也可以在.NET环境下运行,那么首先需要什么呢?根据6. 2节所讲述的内容我们知道,要开发的新语言相当于CIL的高级语言版本,所 以实际上要做什么并不是由新语言决定的,而是由CIL来决定的。因此,需要一套CIL的定 义、规则或标准。这套规则定义了我们的语言可以做什么,不可以做什么,具有哪些特性。 这套规则就称作CTS (Common Type System,公共类型系统)
17、。任何满足了这套规则的高级 语言就可以称为面向.NET框架的语言。C#和VB.NET不过是微软自己开发的一套符合了 CTS 的语言,实际上还有很多的组织或团体,也开发出了这样的语言,比如Delphi. Net、FORTRAN 等。那么CTS具体包括哪些内容呢?在回答这个问题之前我们需要弄清楚一个概念。还是 通过一段C#代码来说明,先看下面几行代码:public class Book /省略实现Book iteml = new Book();Book item2 = new Book ();对于以上代码,通常是这么描述的:定义了一个Book类,并且创建了两个Book类的 实例iteml、item
18、2。实际上这只包含了两层含义如表6-2所示。表6-2类、类的实例类Book类的实例iteml, item2再思考一下就会发现,还有一个更高的层面,那就是Book这个类的类型,我们称之为类类型(Class Type),因此上表可以改成如表6-3所示。表6-3类类型、类、类的实例类类型class类Book类的实例iteml, item2类似的,还有枚举类型(Enum Type) 结构类型(Struct Type)等。现在大家应该 明白这里要表达的意思了,CTS规定了可以在语言中定义诸如类、结构、委托等类型,这些 规则定义了语言中更高层次的内容。因此,在C#这个具体的语言实现中,我们才可以去定 义类
19、类型(Class Type)或者结构类型(Struct Type)等。同样,可以在Book类中定义一个字段name并提供一个方法ShowNameO。实际上,这 些也是CTS定义的,它规范了类型中可以包含字段(filed)、属性(property)、方法(method)、 事件(event)等。除了定义各种类型外,CTS还规定了各种访问性,比如Private、Public、Family (C# 中为 Protected)、Assembly (C#中为 internal) Family and assembly (C#中没有提供实现)、 Family or assembly (C#中为 prote
20、cted internal) oCTS还定义了一些约束,例如,所有类型都隐式地继承自System. Object类型,所有类 型都只能继承自一个基类。从CTS的名称和公共类型系统可以看出,不仅C#语言要满足这 些约束,所有面向.NET的语言都需要满足这些约束。众所周知,传统C+是可以继承自多个 基类的。为了让熟悉C十十语言的开发者也能在.NET框架上开发应用程序,微软推出了面 向.NET的C+/CLI语言(也叫托管C+),它就是符合CTS的C+改版语言,为了满足CTS 规范,它被限制为了只能继承自一个基类。关于上面内容有两点需要特别说明:1)C#并没有提供Family and assembly
21、的实现,C#中也没有全局方法(Global Method)。 换言之,C#只实现了 CTS的一部分功能。,也就是说,CTS规范了语言能够实现的所有能力, 但是符合CTS规范的具体语言实现不一定要实现CTS规范所定义的全部功能。2) C+/CLI又被约束为只能继承自一个基类,换言之,C+中的部分功能被删除了。, 就是说,任何语言要符合CTS,其中与CTS不兼容的部分功能都要被舍弃。显然,由于CIL是.NET运行时所能理解的语言,因此它实现了 CTS的全部功能。虽然 它是一种低级语言,但是实际上,它所具有的功能更加完整。C#语言和CIL的关系,可以用 图6To进行表示。图6-10 C#和CIL的关
22、系1. 5 CLS公共语言规范既然已经理解了 CTS是一套语言的规则定义,就可以开发一套语言来符合CTS 了。假 设这个语言叫做N#,它所实现的CTS非常有限,仅实现了其中很少的一部分功能,它与CTS 和C#语言的关系可能如图6-11所示。图6-11 C#、N#和CIL的关系那么现在就有一个问题:由C#编写的程序集,能够引用由N#编写的程序集吗?答案显 然是不能,虽然C#和N#同属于CTS旗下,但是它们并没有共通之处。因此,虽然单独的 N#或C#程序可以完美地在.NET框架下运行,但是它们之间却无法相互引用。如果使用N#开 发项目的开发者本来就不希望其他语言类型的项目来引用他的项目倒也罢了,但
23、是,如果 N#项目期望其他语言类型的项目能够对它进行引用,就需要N#中公开的类型和功能满足C# 语言的特性,即它们需要有共通之处。注意,这句话中有一个词很重要,就是“公开的”(public) o N#中不公开的部分(private、internal、protected)是不受影响的,可以使 用独有的语言特性,因为这些不公开的部分本来就不允许外部进行访问。因此,如果N#想 要被C#所理解和引用,它公开的部分就要满足C#的一些规范,此时,它与CTS和C#语言的 关系就会变成如图6T2所示。CTS/QL图 6-12 C#、N#、CIL 的关系如果世界上仅有C#和N#两种语言就好办了,把它们共同的语言
24、特性提取出来,然后要 求所有公开的类型都满足这些语言特性,这样C#和N#程序集就可以相互引用了。可问题是: 语言类型有上百种之多,并且.NET的设计目标是实现一个开放的平台,不仅现有的语言经 过简单修改就可以运行在.NET框架上,后续开发的新语言也可以,而新语言此时并不存在, 如何提取出它的语言特性?因此又需要一套规范和标准来定义一些常见的、大多数语言都共 有的语言特性。对于未来的新语言,只要它公开的部分能够满足这些规范,就能够被其他语 言的程序集所使用。这个规范就叫做CLS (Common Language Specification,公共语言规 范)。很明显,CLS是CTS的一个子集。现在
25、引入了 CLS,图6T2的关系图就可以改成如图 613所不。如果创建一个VB.NET类型的项目,实现和上面C#项目完全一样的功能,那么编译后生 成的文件有什么区别?编写控制台应用程序,将字符输出到屏幕,需要调用Console. WriteLineO方法。这个 Console类型从何而来呢?生成的文件在系统中是如何运行起来的?其机制和使用传统VC+生成的可执行文件是 否相同?其实,上面每一个问题的答案都包含.NET框架所提供的支持,这里将它分为三个部分:对于编译后生成的文件格式和内容,.NET中存在着诸多规范。符合这些 规范的程序语言,也叫做面向.NET的语言。编译后生成的文件都可以 在.NET
26、运行时下执行,这就是大家所熟知的.NET多语言支持。在开发阶段,.NET提供了一个庞大的类库,支持开发者快速开发各种应 用程序,也支持程序语言设计者开发其语言编译器。在程序执行阶段,.NET提供了一个程序运行时的环境,这个运行时环境 帮助我们管理内存、实时编译程序、进行安全检查、执行垃圾回收等。接下来就针对上述内容开始为大家详细讲述。1.2 CIL公共中间语言首先要了解的就是C#程序源码在编译之后会得到什么样的一个文件。大家知道,过去 使用VC+生成的可执行文件,经过预编译、编译、汇编、链接几个步骤后,最终生成的可 执行文件中就已经包含了处理器的本地代码(Native Code),支持它运行的
27、只是操作系统 和本地的机器指令集。那么采用C#编译器生成的文件又是什么呢?现在需要引入程序集这 个概念:在.NET框架下,类似C#这样的高级语言经过编译后生成的结果文件被称做程序集, 其后缀名是.dll (类库)或.exe (可执行程序)。在引入这个概念之前,前面(上一节)提 到程序集时,都是用“文件”这个词来描述的。CTS/QL图6-13语言、CLS、CIL的关系如果利用C#开发的一个程序集的公开部分仅采用了 CLS中的特性,那么这个程序集就 叫做CLS兼容程序集(CLScompliant assembly) o显然,对于上面提到的FCL框架类库, 其中的类型都符合CLS,仅有极个别类型的成
28、员不符合CLS,这就保证了所有面向.NET的语 言都可以使用框架类库中的类型。现在,读者又会有一个疑问:上面几段文字中反复出现了一个词“语言特性”(language features),满足CLS就是要求语言特性要一致,那么什么叫做语言特性?这 里给出几个具体的语言特性:是否区分大小写,标识符的命名规则如何,可以使用的基本类 型有哪些,构造函数的调用方式(是否会调用基类构造函数),支持的访问修饰符等。那么我们如何检验程序集是否符合CLS呢?. NET为我们提供了 一个特性CLSCompliant, 便于在编译时检查程序集是否符合CLSo我们来看下面一个例子:using System;assem
29、bly:CLSCompliant (true) public class CLSTest public string name;/警告:仅大小写不同的标识符CLSTest. Name ()不符合CLSpublic string Name() return ;)/警告:“CLSTest.GetValueO”的返回类型不符合CLSpublic uint GetValue() return 0;)/警告:参数类型“sbyte”不符合CLSpublic void SetValue(sbyte a) /警告标识符“CLSTest._aFiled”不符合CLSpublic string MyPropert
30、y get; set; 可以注意到,在CLSTest类的前面为程序集加上了一个CLSCompliant特性,表明这个 程序集是CLS兼容的。但是,有三处并不满足这个要求,因此编译器给出了警告信息。这三 处是:不能以大小写来区分成员,因此字段name和方法Name ()不符合CLS。方法的返回类型和参数类型必须是CLS兼容的,uint和sbyte类型并非 CLS兼容,因此GetValue ()和SetValue ()方法不符合CLS。标识符的命名不能以下划线“,开头,因此属性_MyProperty不符合CLS。还会注意到,编译器给出的只是警告信息,而非错误信息,因此可以无视编译器的警 告,不过这
31、个程序集只能由其他C#语言编写的程序集所使用。1. 6 CLR公共语言运行时1.6.1程序集概述前面提到过:程序集包含了 CIL语言代码,而CIL语言代码是无法直接运行的,需要 经过.NET运行时进行即时编译才能转换为计算机可以直接执行的机器指令。那么这个过程 是如何进行的呢?接下来我们要了解的就是.NET框架的核心部分:CLR (Common Language Runtime), 公共语言运行时),有时也会称做.NET运行时(.NET runtime) o在了解CLR之前,需要 先进一步学习一下程序集,因为下一节会对程序集进行专门的讲述,这里仅简单介绍一下程 序集中对于理解CLR有帮助的概念
32、。从直觉上来看,前面以.exe为后缀的控制台应用程序就是一个直接的可执行文件,因 为在双击它后,它确实会运行起来。这里的情况和面向对象中的继承有一点像:一台轿车首 先是一部机动车、一只猫首先是一个动物,而一个.NET程序集首先是一个Windows可执行 程序。那么什么样格式的文件才是一个Windows可执行文件?这个格式被称做PE/COFF (Microsoft Windows Portable Executab1e/Common Object File Format) , Windows nJ 移植可执行/通用对象文件格式。Windows操作系统能够加载并运行.dll和.exe是因为它能 够
33、理解PE/COFF文件的格式。显然,所有在Windows操作系统上运行的程序都需要符合这个 格式,当然也包括NET程序集在内。在这一级,程序的控制权还属于操作系统,PE/COFF 头包含了供操作系统查看和利用的信息。此时,程序集可以表示成如图6-14所示。图6-14程序集结构1在前面提到过,程序集中包含的CIL语言代码并不是计算机可以直接执行的,还需要 进行即时编译,那么在对CIL语言代码进行编译前,需要先将编译的环境运行起来,因此 PE/COFF头之后的就是CLR头了。CLR头最重要的作用之一就是告诉操作系统这个PE/COFF 文件是一个.NET程序集,区别于其他类型的可执行程序。图6T5程
34、序集结构2在CLR头之后就是大家相对熟悉一些的内容了。首先,程序集包含一个清单(manifest), 这个清单相当于一个目录,描述了程序集本身的信息,例如程序集标识(名称、版本、文化)、 程序集包含的资源(Resources)、组成程序集的文件等。图6-16程序集结构3清单之后就是元数据了。如果说清单描述了程序集自身的信息,那么元数据则描述了程序集所包含的内容。这些内容包括:程序集包含的模块(会在第7章介绍)、类型、类型的成员、类型和类型成员的可见性等。注意,元数据并不包含类型的实现,有点类似于C+中的.h头文件。在.NET中,查看元数据的过程就叫做反射(Reflection) o图6-17程
35、序集结构4接下来就是已经转换为CIL的程序代码了,也就是元数据中类型的实现,包括方法体、 字段等,类似于C+中的.cpp文件。图6-18程序集结构注意,图6-18中还多添加了一个资源文件,例如.jpg图片。从这幅图可以看出,程序 集是自解释型的(Self-Description),不再需要任何额外的东西,例如注册表,就可以完 整地知道程序集的一切信息。至此对程序集的简单介绍就先到这里,接下来看一下程序集是如何被执行的。1. 6. 2运行程序集现在已经了解过了程序集,并且知道程序集中包含的CIL代码并不能直接运行,还需 要CLR的支持。概括来说,CLR是一个软件层或代理,它管理了.NET程序集的
36、执行,主要包 括:管理应用程序域、加载和运行程序集、安全检查、将CIL代码即时编译为机器代码、异 常处理、对象析构和垃圾回收等。相对于编译时(Compile time),这些过程发生在程序运 行的过程中,因此,将这个软件层命名为了运行时,实际上它本身与时间是没有太大关系的。 有一些朋友在初学.NET的时候,纠结在了 Runtime这个词上,总以为和时间有什么关系, 总是不能很好地理解CLR。笔者认为重要的是理解CLR是做什么的,而不用过于关注它的名 称。实际上,CLR还有一种叫法,即VES (Virtual Execution System,虚拟执行系统)。 从上一段的说明来看,这个命名应该更
37、能描述CLR的作用,也不容易引起混淆,但是可能为 了和CIL、CTS、CLS等术语保持一致性,最后将其命名为了 CLR。在这里,我们知道CLR不 过是一个.NET程序集的运行环境而已,有点类似于Java虚拟机。VES这个术语来自于CLL 会在6. 7节进行讲述。可以用图6T9来描述CLR的主要作用。图6-19 CLR的主要作用前面已经概要地了解了 CLR的作用,接下来开始更进一步的学习。首先遇到的问题就是:CLR以什么样的形式位于什么位置?由于CLR本身用于管理托管代码,因此它是由非托管代码编写的,并不是一个包含了 托管代码的程序集,也不能使用IL DASM进行查看。它位于C: %System
38、Root%Microsoft. NETFramework版本号下,视安装的机器不同有两个版本,一 个是工作站版本的mscorwks. dll, 一个是服务器版本的mscorsvr. dll。wks和svr分别代 表 work station 和 server。接下来再看一下CLR是如何运行起来的。虽然从Windows Server 2003开始,.NET框 架已经预装在操作系统中,但是它还没有集成为操作系统的一部分。当操作系统尝试打开一 个托管程序集(.exe)时,它首先会检查PE头,根据PE头来创建合适的进程。接下来会进一步检查是否存在CLR头,如果存在,就会立即载入MsCorEE.dll。
39、这个库 文件是.NET框架的核心组件之一,注意它也不是一个程序集。MsCorEE.dll位于 C:%SystemRoot%Systeni32系统文件夹下所有安装了.NET框架的计算机都会有这个文件。 大家可能注意到了,这个库安装在System32系统文件夹下,而没有像其他的核心组件或类 库那样按照版本号存放在C: %SystemRoot%Microsoft. NETFramework文件夹下。这里又 存在一个“鸡生蛋问题”:根据不同的程序集信息会加载不同版本的CLR,因此加载CLR的 组件就应该只有一个,不能再根据CLR的版本去决定加载CLR的组件的版本。MsCorEE. dll是一个很细的软
40、件层。加载了 MsCorEE. dll之后,会调用其中的 _CorExeMain()函数,该函数会加载合适版本的CLR。在CLR运行之后,程序的执行权就交 给了 CLR。CLR会找到程序的入口点,通常是Main。方法,然后执行它。这里又包含了以下 过程:.加载类型。在执行Main。方法之前,首先要找到拥有Main。方法的类型并 且加载这个类型。CLR中一个名为Class loader (类加载程序)的组件负 责这项工作。它会从GAC、配置文件、程序集元数据中寻找这个类型,然后 将它的类型信息加载到内存中的数据结构中。在Class loader找到并加载 完这个类型之后,它的类型信息会被缓存起来
41、,这样就无需再次进行相同 的过程。在加载这个类以后,还会为它的每个方法插入一个存根(stub) o.验证。在CLR中,还存在一个验证程序(verifier),该验证程序的工作 是在运行时确保代码是类型安全的。它主要校验两个方面,一个是元数据 是正确的,一个是CIL代码必须是类型安全的,类型的签名必须正确。.即时编译。这一步就是将托管的CIL代码编译为可以执行的机器代码的过 程,由CLR的即时编译器(JIT Compiler)完成。即时编译只有在方法的 第一次调用时发生。回想一下,类型加载程序会为每个方法插入一个存根。在调用方法时,CLR会检查方法的存根,如果存根为空,则执行JIT编译过 程,并
42、将该方法被编译后的本地机器代码地址写入到方法存根中。当第二 次对同一方法进行调用时,会再次检查这个存根,如果发现其保存了本地 机器代码的地址,则直接跳转到本地机器代码进行执行,无需再次进行JIT 编译。可以看出,采用这种架构的一个好处就是,.NET程序集可以运行在任何平台上,不管 是Windows、UNIX,还是其他操作系统,只要这个平台拥有针对于该操作系统的.NET框架就 可以运行.NET程序集。1. 7 CLI公共语言基础CLI是一个国际标准,由ECMA和ISO进行了标准化,全称为Common Language Infrastructure (公共语言基础)。它只是一个概念和汇总,实际上本
43、章的每一小节都是这 个标准的一部分。CLI包括:CIL、CTS、CLS、VES、元数据、基础框架。看到这里很多人会感觉到有点奇怪,为什么CLI和.NET框架包含的内容如此雷同?它 们之间是什么关系?简单来说,CLI是一个标准,而.NET框架是这个标准的具体实现。在 CLI中,并没有CLR的概念,只有VES,而CLR就是.NET框架中VES的具体实现。既然CLI 只是一个标准,而.NET框架是它在旧ndows平台上的具体实现,那么是不是就只有NET框 架这一个CLI的实现?显然不是,Mono Project就是CLI标准的另一个实现。Mono Project 的目标就是将.NET框架多平台化,使
44、其可以运行在各种平台上,包括Mac OS、Linux等。CLI的详细信息可以在这里查看: http:www. ecma-international. org/publications/standards/Ecma-335. htm,感兴趣的 朋友可以将它的PDF标准文档下载下来看一下。程序集的定义只是给编译后生成的文件一个稍微正式一点的名称,对于解释“它是由 什么构成的”这个问题并没有太大的帮助。为了进一步了解程序集,我们再来做一个试验, 使用VB.NET创建一个控制台应用程序项目(ConsoleAppVB),并生成一个程序集,代码功 能和上面用C#创建的项目是一样的的。Module Prog
45、ramSub Main()Dim text AsString =hello, world !Console. WriteLine (text)EndSubEndModule现在,需要一个工具来查看这个程序集的内容,并且与C#项目生成的程序集进行对比。 还好,微软已经提供了一个利器IL DASM (IL Disassembler, IL反汇编程序)来帮助 开发者查看程序集的信息。如果安装了 Visual Studio, IL DASM将会随同Visual Studio 一起安装。依次选择开始菜单f Microsoft Visual Studio 2010 f Microsoft Windows
46、SDK Tools -IL反汇编程序(IL DASM)可以启动IL DASMo打开IL DASM后选择VB. NET项目生成的ConsoleAppVB. exe,可以看到如图61所示的 界面。/D:.Net深入解圻DotNetStudyC.口 I回I图6-1 IL DASM运行界面这部分内容很多,会在下一章“程序集”中进行专门讲述,这里暂且略过。展开图6-1中的ConsoleAppVB. Program类型,在Main()方法上双击,会弹出另外一个窗口,显示 图6-2中的代码,看上去有点像汇编语言。在这里可以看到熟悉的string text变量声明及uhello, world !/ ConsoleAppVB.Program:Main : voidQ 查找(F)查找下一个(N) .method public static uoid Main() cil managed .entrypoint .custom instance uoid nscorlibSysten
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
评论
0/150
提交评论