类库主要的好处是它们将核心Win32 API的最常用的功能和外挂SDK的功能封装到了一个统一的包中。采用清晰而有条理的方式对类库进行了分组和描述,这样开发者能更容易地找到他们的应用程序所需的大多数功能。
相反,在过去几年中,新功能要么被“绑缚”到Win32 API上,要由通过独立的API(例如用于图形的Directx,或者用于XML和SOAP的不同的SDK)来提供。对它们唯一能做的逻辑分组就是按照字母顺序进行排序。结果,使用Win32 API和各种SDK经常使人晕头转向,而开发者必须判断几个类似的API中哪一个最适合他们特定的要求。
支持Web Services
CLR和类库的结合使得与以前只是在Windows上相比,开发Web Services更为容易。
首先,CLR为运行服务器应用程序,包括Web Services,提供了一个更可靠的基础。服务器应用程序通常比桌面应用程序要有更高的可用性和安全性的要求,因此它们尤其将从CLR捕捉错误和阻止恶性代码的功能中受益。此外,服务器应用程序通常需要长时间不间断地运行,因此也将从CLR的碎片整理功能中受益。碎片整理功能可以限制内存泄露,否则长时间运行的应用程序可能会耗尽所有可用的内存。
混合可控制代码和不可控制代码
Common Language Runtime(CLR)(通用语言运行环境)的协作功能允许开发者将可控制代码与COM组件中现有的不可控制代码(以及Win32动态连接库(DLL)中的代码)混合起来。
当一可控制代码组件调用一COM组件(顶层)时,CLR就生成一个运行环境可调用包装(runtime callable wrapper)(RCW)。RCW充当不可控制的COM组件的代理(或中介)的角色。RCW处理可控制组件和COM组件之间所有的交互,包括(但不限于)以下内容:
·在CLR和COM环境间翻译和传递数据
·当可控制代码组件被CLR碎片整理进程重新声明时,释放包装的 COM组件的内存和其他资源。
·将来自COM错误返回代码(HRESULT值)的错误翻译成CLR错误(称作异常)。
当COM组件调用用可控制代码(底层)写的 .NET组件时,CLR又生成了一个称作COM 可调用包装(CCW)的包。和RCW类似,CCW也在不可控制的COM代码和可控制代码之间充当代理或中介的角色。CCW还实现了COM组件所需功能的标准设置,这样可控制代码组件看起来就像标准的COM组件一样。
CCW处理不可控制的COM对象和可控制的.NET组件之间的所有支互,包括(但不限于)以下内容。
·在两种环境间移动和翻译数据
·当COM组件被释放时,由CLR释放用于最后的碎片整理的可控制代码。
·将CLR异常翻译为COM返回代码。
其次,类库提供了开发者创建Web Services或使用Web Services的应用程序所需的全部代码。特别地,它们提供了在应用程序数据和XML间进行翻译转换的代码,以及通过Internet协议收发SOAP消息的代码。这样开发者就可将更多的精力放在他们自己的应用程序的逻辑上,而尽量不去考虑如何实现网络协议或读写XML数据这样的细节上。
统一平台:
CLR和类库还联合解决了微软当前平台存在的一个重要问题:所有的编程语言并非是均衡创建的。微软的每种编程语言都有自己的run-time基础结构(例如,Visual Basic [VB] runtime的多个潜在冲突的版本)和软件库(例如Microsoft C++基础类)。这就要求微软维护这些库以及相关的诸如debugger和wizard等工具。一个组织通常不得不将一个项目分割开来,其中一些让C++程序员编写,另外一些则让VB程序员来写。任一种程序员的短缺都会影响进度。
.NET Framework采用以下两种方法来解决语言的划分问题。
标准化数据类型。首先,.NET Framework为最常用的数据类型(例如整数、实数、文本字符)提供了标准的内部描述和运算,并提供了将这些类型向所有的.NET语言和CLR扩展的机制。设立这种标准化数据类型和可扩展模型(全称为.NET Framework Common Type System (CTS)),消除了每种语言用它自己唯一且不兼容的方法实现数据类型的必要。
标准化应用程序格式。其次,.NET Framework实现了一个标准的应用程序格式——拥有自己的MSIL、元数据和清单的汇编。所有.NET语言的编译器都生成这种格式。通过从元数据中提取有关MSIL的信息,编译器、调试器和协议器等工具可以分析处理任何一种源程序设计语言的数据。
标准化的数据类型和应用程序格式使开发者可以创建用任一种理解其中的数据类型和格式的程序设计语言工作的类库,这样的类库包含所有微软的.NET编程语言以及众多的第三方厂商语言。特别地,.NET Framework类库仅使用CTS数据类型,并分配以标准的应用程序格式。结果,这些类库能被使用任何一种.NET编程语言的应用程序所使用。
(请参看“开发可控制代码”示意图。)
CLR和类库相结合为微软提供了一个单一的运行平台,它支持运行所有的编程语言,并且可以用一组公共的开发工具来实现它。微软已经发布了一个该平台和它所使用的语言的规范。(请参看“ECMA标准和Windows Lock-In。)此外,类库向所有的.NET编程语言提供了大致相同的基本功能组,这样就使程序员可以用任一种他们最拿手的语言来工作。
.NET类库域名空间
.NET开发平台提供的API 被组织安排到了一组带有逻辑名的分级域名空间中。(本示意图显示了几个比较重要的类。)这和Win32 API形成了尖锐对比,Win32 API只是一个简单的功能名的长列表,顶多可以按字母排序。有了分级制度以后开发者就可以更加快捷地定位所需的功能,而且添加新的API也不会与已有的发生冲突。
类建立在基础类(底层)之上,基础类具有下述能力:文本处理(System.Text)网络访问(System .NET),以及存储列表和其他数据集(System .Collections)等。
基础类之上是更复杂的类,例如数据访问(System .Data),它包括ADD.NET和XML处理(System .XML)。
顶层是用户接口库。Windows 表单和Drawing库(分别是System.Win表单和System .Drawing)提供了封装后的Windows用户接口,包括GDI+和DirectX .System。Web包含用于建立包括Web Services类和Web 表单用户接口类的ASP.NET应用程序的类库。
开发可控制代码
开发者通过将他们自己的应用程序源代码和来自.NET类库的代码相结合,创建了可控制代码。这些类库可能包括.NET开发平台包含的类库(例如ADO.NET和Windows 表单),以及来自第三方的类库。
接下来.NET编译器将此代码从人可读的格式翻译成Microsoft Intermediate Language (MSIL)。不管采用何种语言,所有的.NET开发平台编译器均生成MSIL结果。
除了MSIL,.NET编译器还产生元数据,它描述了弥补代码的组件。Common Language Runtime (CLR)(通用语言运行环境)使用这种元数据来增强安全性,并确保获得它所需的任何组件的正确版本(减少组件冲突,或者“DLL Hell”)。
Visual Studio .NET和其他工具自动将MSIL代码封装到CLR中使用的汇编中。几个MSIL文件可以被组合成一个单一的汇编。(有关一个汇编如何由CLR来执行的图解概貌,请参看“执行可控制代码”示意图。)
6.NET开发平台与J2EE的比较
作为彼此竞争的应用程序平台,微软 的.NET开发平台和Sun 的Java 2 Enterprise Edition(J2EE)(Java 2企业版)在意图和体系上极其相似,但在底层实现上却完全不同。
类似的目标 :
.NET开发平台和J2EE在精神实质上具有类似的目标:
Ø 采用更易于重用别人创建的代码组件的程序设计模型,通过向开发者提供已有的组件,消除了重写底层例程的必要,从而提高开发者的开发效率。
Ø 通过消除或减少对C这样的开发语言的易出错结构的使用,以及使用强迫对所有代码组件间的交互点作清晰定义的编程模型(这隔离了错误的影响,并且使错误跟踪更为容易),增强了软件的可靠性。
Ø 通过对应用程序可以或不可以做什么(例如它们是否可以读/写磁盘)加以控制,并且在运行时采用数字签名以确认代码是由信任的实体编写的且尚未被改变,来提高安全性。
Ø 通过在代码自身内嵌入组件描述(包括版本信息)来简化安装和卸载。这免除了让开发者在安装时“注册”他们的代码的思想——这是以前安装复杂和不稳定的一个主要原因—— 从而使需要时,没有或很少有用户或者管理员的干预,应用程序软件即可自动安装成为可能。在.NET开发平台的情形中,它还允许同一组件的不同版本共存于一个系统,彼此间互不干涉,也不与其他应用程序相干涉。
类似的体系结构:
由于目标类似,.NET和J2EE两个开发平台也有着类似的体系结构。相应的体系结构特征如下:
Ø 虚拟机:设计它用来检查、加载和执行在一个牢牢受控的“沙箱”(sandbox)中的程序。通过在程序代码可以做和不可以做什么之间设置严格的边界,这个沙箱减少了由恶性代码(例如病毒)和信任代码偶然的行为造成的危险。为了启用这个沙箱体系结构,所有的程序都被从原始代码编译成了与处理器无关的中介语言——Microsoft Intermediate Language(MSIL)或Java位码。然后在称作Just-in-Time(JIT)编译器的参与下,这些中介代码单元被翻译成了针对特定CPU类型和操作系统的本机代码。这个虚拟机还向程序提供了诸如内存管理等基础服务。.NET的虚拟机称作Common Language Runtime(CLR),J2EE使用Java Virtual Machine(JVM)(Java虚拟机)。
Ø 类库:向应用程序开发者提供预先写好的功能,包括:编码服务(例如字符串操作和事务处理),网络服务(协议处理),系统管理服务(安全许可和组件合并),服务器服务(为Web页服务,连结E-mail),以及连结外部源(例如数据库系统和数据流)的服务。
Ø 定制的编程语言:建立在C和C++基础之上,包括诸如强类型化和能提高开发者开发效率并降低bug出现的可能性等改进。不过,只要有编译器能将初始的源代码翻译成为虚拟机能够理解的中介代码,就没有必要用这些语言(C# for .NET或者Java for J2EE)来写程序。CLR现在支持C#、Visual Basic、 Jscript、 COBLOL、 Fortran、 Haskell以及Python(由的三方开发的带有许多其他语言的工具);JVM支持Java、COBOL、ADA以及Prolog等。
Ø 用于运行在Web服务器上的动态Web页的开发环境:这让开发者使用相同的平台既可创建桌面应用程序,又可创建基于Web的应用程序,.NET使用ASP..NET,而J2EE使用Java Server Pages(JSP)。
7. .NET开发平台工具:
和先前从Win16到Win32 API的平台转换不同,从Win32到.NET开发平台的转换既有对已有语言和工具的修改,还引入了全新的语言。结果,决定使用.NET开发平台的组织,不仅必须改变它们的平台战略,而且还必须考虑它们的语言和工具战略。
.NET开发平台语言
将有三种新版的微软编程语言支持CLR和类库:Visual Basic.NET, Visual C++,以及Jscript.NET。它们还将结合两种新语言:Visual C#和Visual J#。Visual J#使visual J++开发者可以使用类似的语言创建可控制代码。
微软经常指出,.NET开发平台和诸如Java等其他编程环境之间的最大的差别在于,.NET开发平台支持多种编程语言。(有关.NET开发平台与Java之间差别的更多信息,语参看边框内容 (“.NET开发平台与J2EE的比较”。)由于.NET开发平台支持不同的语言,具有不同技巧的程序员就可以使用他们最擅长的语言来创建组件,而这些组件可以平滑地协作。但这也带来一个问题——开发和项目经理如何选择他们的应用程序所用的语言。
Microsof的每一种支持CIR和类库的语言都有着不同的实现和历史,做选择时需要加以考虑。(为获得选择.NET开发语言的快速指南,请参看边框内容“选择.NET语言的经验规则”。)
Visual Basic .NET
这种新的语言拥有与现有的Visual Basic(VB)类似的语法,设计它的目的是为了让使用VB的开发者能过渡到.NET。不过,和以前的VB版本不同的是,Visual Basic.NET使用CLR和类库取代了类似的VB组件和插件。VB.NET还有新的、高级的功能,例如对多线程和结构化异常处理的支持。尽管如“onerror goto”型的错误处理的语言习惯的去除是一项受欢迎的改变——这会使应用程序更加健壮,但却意味着现在的VB程序员不能加载并运行他们以前的应用程序。
事实上,VB.NET与以前的VB版本相比有很大的改变,不能向后兼容。微软正在开发一个工具,用于将VB源代码迁移成VB.NET代码,但是这个过程不能全部自动完成。开发者必须手工检查迁移后的代码,重写某些部分,并仔细测试结果。
不过,开发者不必一次迁移所有代码:幸赖CLR的协作功能,VB.NET可以调用VB代码,反之亦然。这就允许开发者逐渐递增地迁移应用程序——例如,一个VB.NET应用程序可以合并一些已有的VB模块。
由于迁移不能马上完成,微软答应它将继续支持现在的VB语言(6.0版),至少到VB .NET的第三版发布,根据VB发布的惯常速度,那大概要等到五、六年之后。
两个VB的变种根本不能迁移到.NET开发平台上:一种是Visual Basis Scripting Edition(VBScript)(Visual Basic脚本描述版本),用于管理脚本、Active Server Pages (ASP)(活动服务器页)与动态Web内容的脚本描述语言;另一种是Visual Basic for Applications (VBA),用于定制诸如Office等应用程序的脚本描述语言。VBScript已经包容在VB.NET中,而VBA则将继续作为Office中的宏程序设计语言发挥作用。
微软说在向.NET开发平台迁移时,过去使用VB的开发者应使用VB.NET而非C#。这只是一个初步分析的结论,具体情况还需考虑开发者使用的VB功能的广泛程度:
·对于多数一般的VB程序员,大多数的语言改变相当直接。如果VB开发者的主要经验是使用已有的VB组件,那么他们应当使用VB.NET进行新应用程序的开发,而不能转到使用C#上去。像C#这样的更为严格的面向对象语言的附加的复杂性与任何获得的小的收益都不成比例。
·高级的VB程序员——例如,那些广泛使用诸如“Win32 Declare”这类对底层OS进行直接调用的功能的开发者——则另当别论。使用VB.NET,他们现在能发挥自己的本领创建应用程序底层的组件,例如那些供其他VB程序员使用的组件。不过,因为他们要设计供团队内其他成员使用的组件(即使团队的其他人继续使用VB.NET),这些组件开发者也应考虑切换到C#对于组件开发的好处。