C#学习笔记一:CLR & C# 基础

写在前言

.Net Framework并不是Win 32 API 和COM上的一个抽象层。

某种程度上,它是自己的操作系统,有自己的内存管理器,自己的安全系统,自己的文件加载器,自己的错误处理机制,自己的应用程序隔离边界(AppDomains),自己的线程处理模型等。

随着多核计算机越来越普遍,线程处理,并发执行,并行结构,同步等方面的重要性日益凸显。

CLR的执行模型

 

公共语言运行时 CLR Common Language Runtime

是一个运行时环境,保证应用和底层操作系统之间必要的分离,是.NET Framework的主要执行引擎。是可由面向CLR的多种编程语言使用的“运行时”。CLR的核心功能(内存管理、程序集加载、安全性、异常处理和线程同步等)由面向CLR的所有语言使用。CLR不关心开发人员使用哪一种语言来写源代码。也就是说挑选编程语言时,应该选择最容易表达自己意图的语言。理论上,可以用任何语言编写代码,只要编译器是面向CLR的就可以了。

编译器

可以视为语法检查器和“正确代码”的分析器。它们检查源代码,确定你写的一切都有意义,然后输出对你的意图进行描述的代码。不同的编程语言,有着不同的语法。不要低估这个选择的价值,也许会节省大量的开发时间。

Microsoft已经创建好几个面向“运行时”的语言编译器,包括:C++/CLI、C# (C sharp)、Visual Basic、F#、Iron Python、Iron Ruby以及一个“中间语言”(Intermediate Language, IL)汇编器。

IL代码 (托管代码)

本地代码编译器是面向特定CPU架构的代码。而每个面向CLR的编译器生成的都是IL代码 (中间语言代码 。IL代码有时称为托管代码,因为CLR要管理它的执行。它明显的优势在于它是CPU无关的。

元数据

IL代码由面向CLR的编译器产生,但它并不是编译器产生的提供给运行时仅有的东西。编译器同样产生有关原始代码的元数据。它提供给CLR关于代码更多的东西,例如:各种类型的定义、各种类型成员的签名以及其他数据。基本上,元数据是类型库、注册表内容和其它用于COM的信息。尽管如此,元数据还是直接和执行代码合并在一起,并不处在 隔离的位置。

简单地说,元数据是整个microsoft .net framework开发平台的关键,它实现了编程语言、类型和对象的无缝集成。

程序集 (assembly)

一个抽象的概念。首先,他是一个或多个模块/资源文件的逻辑性分组。其次,程序集是重用、安全性以及版本控制的最小单元。取决于你对编译器或者工具的选择,即可以生成单文件程序集,也可以生成多文件程序集。在CLR的世界中,程序集相当于一个“组件”。利用“程序集”这个概念性的东西,可以将一组文件当成一个单独的实体来对待。

对于一个可重用的、可保护的、可版本控制的组件,程序集把它的逻辑表示和物理表示分开。具体如何将代码和资源划分到不同的文件中,完全取决于个人。程序集的模块中,还包含与引用的程序集有关的信息。这些信息使程序集能够自描述(self-describing)。换句话说,CLR能够判断出为了执行程序集中代码,程序集的直接依赖对象(immediate dependency)是什么。

托管程序集同时包含元数据IL。IL是与CPU无关的机器语言,是Microsoft在请教了外面的几个商业及学术性语言/编译器的作者之后,费劲心思开发出来的。IL比大多数CPU机器语言都要高级。IL能访问和操作对象类型,并提供了指令来创建和初始化对象,调用对象上的虚方法以及直接操作数据元素。甚至可以提供抛出和捕捉异常的指令来实现错误处理。可将IL视为一种面向对象的机器语言

重要的提示:

允许在不同编程语言之间方便地切换,同时又保持紧密集成,这事CLR的一个非常出色的特性。遗憾的是,许多开发人员都忽视了这一特性。例如,C#和Visual Basic等语言能很多地执行I/O操作,APL语言能很好地执行高级工程或者金融计算。通过CLR,应用程序的I/O部分可用C#编写,工程计算部分则换用APL编写。CLR在这些语言之间提供了其他技术无法媲美的集成度,使“混合语言编程”成为许多开发项目的一个值得慎重考虑的选择。

执行一个方法,首先必须把它的IL转换成本地CPU指令,这是CLR的JIT (just-in-time或者“即时”)编译器的职责。JITCompiler 是CLR的一个组件,称为JITer 或者JIT编译器。它在定义(某一个类型)程序集的元数据中查找被调用的方位的IL, 接着验证IL代码,并将IL代码编译成本地CPU指令。本地CPU指令被保存到一个动态分配的内存块中。

一个方法只有在首次调用时才会造成一些性能损失。以后对该方法的所有调用都以本地代码的形式全速运行,无需重新验证IL并把它编译成本地代码。

JIT编译器将本地CPU指令存储到动态内存中,一旦应用程序终止,编译好的代码也会被丢弃。所以,如果将来再次运行应用程序,或者同时启动应用程序的两个实例(使用两个不同的操作系统进程),JIT编译器必须再次将IL编译成本地指令。

对于大多数应用程序来说,因JIT编译器造成的性能损失并不显著。大多数应用程序都会反复调用相同的方法。在应用程序运行期间,这些方法只会对性能造成一次性的影响。另外,在方法内部花费的时间很有可能比花在调用方法上的时间多得多。

还需要特别注意的是:

CLR的JIT编译器会对代码进行优化,这类似于非托管的C++编译器的后端所做的工作。同样地,可能花费较多的时间来生成优化的代码。优化之后的代码将获得更加出色的性能。

非托管的饭吗是针对一种具体的CPU平台编译的,一旦调用,代码直接就能执行。但是在托管环境中,代码的编译是分成两个阶段完成的。首先,编译器遍历源代码,做尽可能多的工作来生成IL代码,而为了真正的执行调用,这些IL代码本身必须在运行时编译成本地CPU指令,这需要分配更多的内存,并需要花费额外的CPU的时间。实践确实表明,运行时发生的第二个编译阶段会影响性能,会分配动态内存。但是,Microsoft进行了大量性能优化的工作,将这些额外的开销保持在最低限度。

IL和验证

IL是基于栈的。由于IL没有提供操作寄存器的指令,所以人们可以很容易的创建新的语言和编译器,生成面向CLR的代码。

IL指令还是“无类型”(typeless)的。例如,IL提供了一个add指令,它的作用是将压入栈的最后两个操作数加到一起。add指令不分32位和64位版本。

IL的亮点是它对底层CPU的抽象,但这并非它的最大优势。IL提供的最大的优势在于应用程序的健壮性和安全性。将IL编译成本地CPU指令时,CLR会执行一个名为验证(verification)的过程,这个过程会检查高级IL代码,确定代码所做的一切都是安全的。如,验证会核实调用的每个方法多有正确数量的参数,传给每个方法的参数都具有正确的类型,每个方法的返回值都得到了正确的使用,每个方法都具有一个返回语句等等。在托管模块的元数据中,包含了要由验证过程使用的所有方法和类型信息。

将每个windows进程都放到一个独立的地址空间,将获得健壮性和稳定性,一个进程无法干扰另一个进程。通过验证 托管代码,确保代码不会不正确的访问内存,不会干扰到另一个应用程序的代码。这样一来,就可以放心地将多个托管应用程序放到一个Windoes虚拟地址空间中运行。

CLR提供了在 一个操作系统进程中执行多个托管应用程序的能力。每个托管的应用程序都在一个AppDomain中执行。默认情况下,每个托管的exe文件都在它自己的独立地址空间中运行,这个地址空间只有一个AppDomain。然而,CLR的宿主进程(比如IIS或者MS SQL Server)  可决定在单个操作系统进程中运行多个AppDomain。

通用类型系统

CLR是完全围绕类型展开的,这一点到现在为止应该很明显了。类型为应用程序和其他类型公开了功能。通过类型,用一种编程语言写的代码能与另一种语言写的代码沟通。由于类型是CLR的根本,所以Microsoft指定了一个正式的规范,叫做“通用类型系统”(Common Type System, CTS), 描述类型定义和行为。利用了CTS指定的规则,程序集为一个类型建立了可视边界,CLR则强制(贯彻)了这些规则。

事实上,并不需要去学习CTS规则本省,你选择的语言会采用你熟悉的公式公开它自己的语言语法与类型规则。通过编译来生成程序集时,它会将语言特有的语法映射到IL -- 也就是CLR的“语言”。

CLR让我们意识到:“代码的语言”和“代码的行为”。不同语言可以定义系统的类型,添加相同的成员,语法有不同,但是类型的行为都是完全一致的,因为最终由CLR的CTS来定义类型的行为。

--------------------------------------------------------------------

时间: 2024-12-14 18:05:25

C#学习笔记一:CLR & C# 基础的相关文章

Linux程序设计学习笔记----Socket网络编程基础之TCP/IP协议簇

转载请注明出处: ,谢谢! 内容提要 本节主要学习网络通信基础,主要涉及的内容是: TCP/IP协议簇基础:两个模型 IPv4协议基础:IP地址分类与表示,子网掩码等 IP地址转换:点分十进制\二进制 TCP/IP协议簇基础 OSI模型 我们知道计算机网络之中,有各种各样的设备,那么如何实现这些设备的通信呢? 显然是通过标准的通讯协议,但是,整个网络连接的过程相当复杂,包括硬件.软件数据封包与应用程序的互相链接等等,如果想要写一支将联网全部功能都串连在一块的程序,那么当某个小环节出现问题时,整只

加壳学习笔记(一)-基础知识

1.预备知识 1.关于栈,在windows里面的堆栈其实很简单,当学了才知道哈,呵呵,第一要记住的是windows里面的栈是向低地址生长的(extended,延伸,呵呵,顺便丰富下英语的单词量,确实是少的可怜),你可以这样认为,栈就像是一个倒立的箱子,箱子的口子是向下的,底是向上的,这里就表明了系统栈的分布也是延伸方向是由高地址向低地址extended,在最初的空栈阶段,栈顶(extended stack pointer,简称是esp)在栈底的低一个位置,呵呵,其实很好理解,就是说最初的箱子是空

MongoDB 学习笔记一 安装以及基础命令

一.MongoDB安装配置 1.获取最新版本: wget http://fastdl.mongodb.org/linux/mongodb-linux-x86_64-2.0.2.tgz 2.解压缩即可执行 tar zxvf mongodb-linux-x86_64-2.0.2.tgz tar zxvf mongodb-linux-x86_64-2.0.2.tgz cd /usr/mongodb-linux-x86_64-2.0.2/bin 但是在运行前,需要创建mongodb需要的存放数据和日志的

汇编入门学习笔记 (一)—— 基础知识、寄存器

疯狂的暑假学习之  汇编入门学习笔记 (一) 参考:<汇编语言> 王爽  第一,二章 一.基础知识 1. 用汇编语言编写程序的工作过程 汇编本质就是为了方便程序员,把二进制代码用汇编指令来表示 汇编指令---------------->  编译器  ---------------->机器码----------------> 计算机执行 mov ax, bx                                                          100

MongoDB 学习笔记(一)基础篇

1.MongoDB 特点 面向集合存储,存储对象类型的数据方便 模式自由,不需要定义任何模式(schma) 动态查询 完全索引,包含内部对象 复制和故障恢复方便 高效的二进制数据存储 支持c# 平台驱动 2.体系结构 一台服务器可以创建多个Server 实例和数据库,(推荐一天server 机器创建一个实例), 数据库:MongoDB 中的一系列与磁盘有关的物理文件(数据文件,日志文件等). 数据逻辑结构:文档 (documnet) 集合(collection) 数据库(database). d

《solidity学习笔记》chapter 2-solidity基础知识

映射 映射本质上是存储和查找数据所用的键-值对. mapping (uint => string) intToStr; 地址 以太坊区块链由 account (账户)组成,你可以把它想象成银行账户.一个帐户的余额是 以太 (在以太坊区块链上使用的币种),你可以和其他帐户之间支付和接受以太币,就像你的银行帐户可以电汇资金到其他银行帐户一样.每个帐户都有一个"地址",你可以把它想象成银行账号.这是账户唯一的标识符. mapping (address => uint )publi

java学习笔记14--多线程编程基础1

本文地址:http://www.cnblogs.com/archimedes/p/java-study-note14.html,转载请注明源地址. 多线程编程基础 多进程 一个独立程序的每一次运行称为一个进程,例如:用字处理软件编辑文稿时,同时打开mp3播放程序听音乐,这两个独立的程序在同时运行,称为两个进程 进程要占用相当一部分处理器时间和内存资源 进程具有独立的内存空间 通信很不方便,编程模型比较复杂 多线程 一个程序中多段代码同时并发执行,称为多线程,线程比进程开销小,协作和数据交换容易

c 语言学习笔记(一)基础

近期工作上有对C语言算法上的需求,所以要学C,上学的时候没学过,只学过半年的Java(我是专升本,本科学的材料),2015年工作后也学过C,那时候的需求是能看懂就可以,也就没深入研究,用一周撸了一遍C基础,可以看懂了,现在要能自写出来,而且是算法相关的,两年过去了,一些细节更是早就忘光了,只能再深入学习一下了.最后说一句,每个人学东西都是从不会开始,除了班禅我从未听说有人生下来就会需要后天习得的技能,即便是动物也是通过游戏来习得捕猎的,所以说别怕晚,3个月你就可以入门了,而且除了相对论这种接近于

Typescript学习笔记(一)基础类型

为了面向ng2和前端未来,开始搞向ts,ts是微软出的一枚语言,作为es6的超集,他出的一些特性还是蛮好用的(略坑).对于我等纯前端(从开始就接触javascript)的人来说,真想说,这特么什么鬼.部分特性同es6(个人对es6还是蛮有好感的).ts同期的coffeescript,将js python化,ts也把js搞的向其他语言靠拢.. 中文学习,这里是英文学习.如果不想看这些东西,那看我笔记学吧.哈哈. ts的基础类型,布尔值,数字,字符串,数组,元组(Tuple),枚举,任意值,空值.后

[Python学习笔记1]Python语言基础 数学运算符 字符串 列表

这个系列是我在学习Python语言的过程中记录的笔记,主要是一些知识点汇总,而非学习教程,可供有一定编程基础者参考.文中偏见和不足难以避免,仅供参考,欢迎批评指正. 本系列笔记主要参考文献是官网文档:http://docs.python.org/.在此向文档编辑者致谢.请勿将本文用于商业用途. 一.Python语言介绍 首先,Python是一种广泛应用的通用高级编程语言,具有较高的抽象层次,支持面向对象的编程方法.其具有高级的数据结构和许多方便的库文件,可以完成文件IO.系统调用.网络编程,甚至