.NET之道

  在微软发布C#语言和.NET平台之前,为Windows操作系统家族创建应用程序的开发者常常使用COM编程模型。COM(Component Object Model,组件对象模型)允许个人构建可由不同编程语言共享的代码库。例如,Visual Basic开发者可以使用C++程序员构建的COM库。COM的语言无关特点自然十分有用,但它复杂的基础结构、脆弱的部署模型常常带来很多麻烦,并且只能部署在Windows操作系统上。

  尽管COM有很多复杂性和局限性,但不计其数的应用程序还是成功地构建于这个基础结构之上。然而在今天,大多数为Windosw操作系统家族创建的应用程序都不是COM模型构建的。桌面应用、网站、操作系统服务、数据访问或业务逻辑复用库都是使用.NET平台创建的。

.NET平台的主要优点

  C#和.NET平台是2002年正式发布的,当时主要为了提供一种比COM更强大、更灵活、更简洁的编程模型。.NET Framework用于在Windows系列操作系统和其他如Mac OS X或Unix/Linux等非微软的操作系统中创建系统。为了打好基础,先来快速浏览一下.NET Framework的一些核心功能:

  • 对已有代码具有完全的互操作性:这(当然)是一件很好的事情。已有的COM二进制组件可以和更新的.NET二进制组件共存,反之亦然。在.NET4.0及后续版本,使用dynamic关键字可以进一步简化这种互操作性。
  • 支持多种编程语言:使用多种编程语言(C#、Visual Basic、F#等)创建.NET应用。
  • 所有支持.NET的语言共享的公共运行时引擎:这个引擎的一个特点是具有一组明确定义的类型,而每一种支持.NET的语言都能“明白”这些类型。
  • 语言集成:.NET支持跨语言的继承、异常处理和代码调试。比方说,C#中定义的基类可以在Visual Basic进行扩展。
  • 全面的基础类库:这个库除隐藏了原始API调用的复杂性外,还提供了被所有支持.NET的语言所使用的一致的对象模型。
  • 简化的部署模型:与COM不同,.NET库不需要将二进制单元注册到系统注册表了。另外,.NET允许同一个*.dll的不同版本存在于同一台机器上。

 

.NET平台构造块(CLR、CTS和CLS)简介

  了解了.NET的优点之后,让我们来预览一下使.NET成为现实的3个关键(而且相互关联的)实体:CLR、CTS和CLS。从程序员的角度看,.NET可以理解为一个运行库环境和一个全面的基础类库。运行库层的正式名称是CLR(Common Language Runtime,公共语言运行库)。其主要作用是为我们定位、加载和管理.NET类型,同时也负责一些底层细节的工作,如内存管理、应用托管。处理线程、安全检查等。

  .NET平台的另一个构造快是CTS(Comman Type System,公共类型系统)。CTS规范完整描述了运行库所支持的所有可能的数据类型和编程结构,指定了这些实体间如何交互,也规定了它们在.NET元数据格式中的表示。

  要注意的是,一种特定的支持.NET的语言可能不支持CTS所定义的所有特性。CLS(Common Language Specification,公共语言规范)是一个相关的规范,定义了一个让所有.NET语言都支持的公共类型和编程结构的子集。这样,如果构造的.NET类型仅公开与CLS兼容的特性,那么可以肯定其他所有支持.NET的语言都能使用它们。反之,如果使用了与CLS不兼容的数据类型或编程结构,就不能保证所有的.NET语言能和你的.NET代码库交互。庆幸的是,让C#编译器遵从CLS来验证代码是十分简单的。

基础类库的作用

  除了CLR和CTS/CLS规范之外,.NET平台提供了一个适用于全部.NET程序语言的基础类库(BCL)。这个基础类库不仅封装了各种基本类型,如线程、文件输入/输出(I/O)、图形绘制以及与各种外部硬件设备的交互,还支持在实际应用中用到的一些服务。

  例如,基础类库定义了一些可创建任意类型软件应用程序的类型,例如,使用ASP.NET创建Web站点,使用WCF创建网络服务,使用WPF创建桌面GUI应用程序,等等。基础类库还定义了另外一些类型,可以与特定计算机上的XML文档、本地目录和文件系统互动,通过ADO.NET与关系数据库交流,等等。如图1所示,可以从宏观上看到CLR、CTS、CLS和基础类库之间的关系。

图1 CLR、CTS、CLS和基础类库之间的关系

C#的优点

  C#的核心语法和Java语法相似。本质上,C#和Java都属于C语言系列(包括C、Objective C、C++等),它们有类似的语法。

  实际上,C#的许多语法结构与VB和C++的很多方面都有渊源。例如,与VB类似,C#支持类型属性(property)(与传统的获取方法和设置方法相反)和可选参数。与C++类似,C#允许重载操作符,且支持创建结构、枚举和回调函数(使用委托)。

  此外,C#支持各种函数式语言(如LISP或Haskell)中的很多特性,例如Lambda表达式和匿名类型。此外,由于LINQ的出现,C#支持很多编程结构,在编程语言中显得非常独特。尽管如此,C#的核心始终受到C系列语言的影响。

  C#是多种语言的混合体,因此它像Java一样语法简洁,想VB一样使用简单,像C++一样功能强大和灵活。以下是C#核心特征的一部分,其中大部分特点也是其他支持.NET的程序语言所共有的特征。

  • 不需要指针!C#程序通常不需要直接对指针进行操作(尽管在绝对必要时也能自由地进行底层操作
  • 垃圾收集器能够自动管理内存。因此,C#不支持delete关键字。
  • 类、接口、结构、枚举和委托都有正式的语法结构。
  • 具有与C++类似的功能,可以简单地重载操作符为自定义类型(例如,不需要操心确保“返回*this以能够链接”)。
  • 支持基于特性的编程。这种方式的开发允许我们注释类型及其成员来进一步限定其行为。例如,用这个[Obsolete]特性标记某种方法后,后面再使用这种方法的时候就会打印自定义的警告信息。

  随着.NET 2.0发布(大约2005年),C#编程语言被更新以支持很多花哨的东西,主要是以下几项。

  • 构建泛型类型和泛型成员的能力。使用泛型,我们可以构建非常高效的并且类型安全的代码,在和泛型项交互的时候可以定义很多占位符。
  • 支持匿名方法,它允许我们在任何需要委托类型的地方提供内联函数。
  • 使用partial关键字跨多个代码文件定义单个类型的能力(或者如果有必要的话,可以作为内存中的表示)。

  .NET 3.5(大约发布于2008年)为C#编程语言增加了更多功能,包括如下特性。

  • 支持强类型的查询(如LINQ),可用于和各种形式的数据进行交互。
  • 支持匿名类型,它允许我们建模一个类型的形(shape)而不是其行为。
  • 使用扩展方法扩展既有类型(没有子类)功能的能力。
  • 包含了Lambda操作符(=>),它可以进一步简化.NET委托类型的使用。
  • 新的对象初始化语法,它允许我们在创建对象时设置属性的值。

  .NET 4.0(2010年发布)再次为C#添加了少量特性,下面举几个例子。

  • 支持可选的方法参数和命名的方法参数。
  • 支持通过dynamic关键字在运行时动态查找成员。提供了一个统一的方法用于在运行时调用成员,而不必理会成员的实现框架(COM、IronRuby、IronPython或通过.NET反射服务)。
  • 泛型类型的操作将更加直观,因为可以使用逆变和协变,轻易地在泛型数据和普通的System.Object集合之间进行相互映射。

  最后是随着.NET 4.5发布的C#当前版本。C#当前版本提供了一对关键字(async和await),极大地简化了多线程和异步编程。如果你使用过以前版本的C#,一定会记得通过副线程调用方法需要大量的含义模糊的代码,并使用不同的.NET命名空间。而现在C#提供了语言关键字来为我们处理这种复杂性,异步调用方法的过程几乎像以同步方式调用方法一样简单。

托管代码与非托管代码

  关于C#语言,要理解的最重要的一点可能是,它生成的代码只能在.NET运行库中执行(你不能用C#来构建本机的COM服务器或非托管的C/C++ API应用程序)。正式的说法是,这种必须在.NET运行库下执行的代码称为托管代码(managed code)。这些包含托管代码的二进制单元称为程序集(assembly)。反之,不能直接在.NET运行库承载(host)的代码称为非托管代码(unmanaged code)。

 

其他支持.NET的编程语言

  应该知道,C#并不是构建.NET应用的唯一一种语言。在安装Visual Studio时,你将得到5种托管语言:C#、Visual Basic、C++/CLI、JavaScript和F#。

  除了微软提供的托管语言之外,还有Smalltalk、Ruby、Python、COBOL和Pascal的.NET编译器等。

多语言世界中的生活

  当初步了解.NET的语言无关性后,开发者会提出许多问题。其中最普遍的问题可能就是:“如果所有的.NET语言都会编译成‘托管代码’,为什么我们还需要多种编译器呢?”

  这个问题有许多个答案。首先,程序员在选择编译语言时有各自不同的喜好。

  现在,平心而论,如果微软推出了一门派生自BASIC语言系列的“官方”.NET语言,你认为所有程序员会喜欢这样的选择吗?或者,如果这个唯一的“官方”.NET语言是基于Fortran语法的,那么可以想象所有人都会对.NET置之不理。因为.NET运行库并不在意一段托管代码是由哪种语言生成的。所以.NET程序员可以继续使用它们熟悉的语法,且与组员、部门甚至其他公司共享编译的程序集(不用管他们用的是那种.NET语言)。

  将各种.NET语言集成为一个统一软件方案的另一个好处,就是能够取长补短。所有的编程语言都有各自的有点和缺点。例如,一些编程语言对高级的数学处理有相当完美的内在支持能力。另一些则精于支持财务计算、逻辑计算和大型机交互等。当你学习到某种编程语言的优点并将其融合到.NET平台时,大家就都能受益。

posted @ 2017-02-17 10:16  KUYUTI  阅读(166)  评论(0编辑  收藏  举报