C#锐利Word下载.docx

上传人:b****5 文档编号:18890321 上传时间:2023-01-02 格式:DOCX 页数:21 大小:54.82KB
下载 相关 举报
C#锐利Word下载.docx_第1页
第1页 / 共21页
C#锐利Word下载.docx_第2页
第2页 / 共21页
C#锐利Word下载.docx_第3页
第3页 / 共21页
C#锐利Word下载.docx_第4页
第4页 / 共21页
C#锐利Word下载.docx_第5页
第5页 / 共21页
点击查看更多>>
下载资源
资源描述

C#锐利Word下载.docx

《C#锐利Word下载.docx》由会员分享,可在线阅读,更多相关《C#锐利Word下载.docx(21页珍藏版)》请在冰豆网上搜索。

C#锐利Word下载.docx

}}我们可以打开Windows自带的简易的"

记事本"

程序来编写这段代码--笔者推荐刚开始采用这个极其简单却能把程序代码暴露的相当清晰的编辑工具.我们将它的文件名保存为HelloWorld.cs,其中"

.cs"

是C#源代码文件的扩展名.然后在配置好C#编译器的

命令行环境里键入"

cscHelloWorld.cs"

编译文件.可以看到编译输出文件HelloWorld.exe.我们键入HelloWorld执行这个文件可得到下面的输出:

HelloWorld!

下面我们来仔细分析上面的代码和整个程序的编译输出及执行过程.先看文件开始的两行代码,这是C#语言的单行注释语句.和C++语言类似,C#支持两种注释方法:

以"

//"

开始的单行注释和以"

/*"

"

*/"

配对使用的多行注释.注释之间不能嵌套.再来看下面的"

usingSystem;

语句,这是C#语言的using命名空间指示符,这里的"

System"

是Microsoft.NET系统提供的类库.C#语言没有自己的语言类库,它直接获取Microsoft.NET系统类库.Microsoft.NET类库为我们的编程提供了非常强大的通用功能.该语句使得我们可以用简短的别名"

Console"

来代替类型当然using指示符并不是必须的,我们可以用类型的全局名字来"

System.Console"

.获取类型.实际上,using语句采用与否根本不会对C#编译输出的程序有任何影响,它仅仅是简化了较长的命名空间的类型引用方式.接着我们声明并实现了一个含有静态Main()函数的HelloWorld类.C#所有的声明和实现都要放在同一个文件里,不像C++那样可以将两者分离.Main()函数在C#里非常特殊,它是编译器规定的所有可执行程序的入口点.由于其特殊性,对Main()函数我们有以下几条准则:

1.Main()函数必须封装在类或结构里来提供可执行程序的入口点.采用了完全C#的面向对象的编程方式,C#中不可以有像C++那样的全局函数.2.Main()函数必须为静态函数(static).这允许C#不必创建实例对象即可运行程序.3.但一Main()函数保护级别没有特殊要求,public,protected,private等都可,般我们都指定其为public.4.Main()函数名的第一个字母要大写,否则将不具有入口点的语义.C#是大小写敏感的语言.5.Main()函数的参数只有两种参数形式:

无参数和string数组表示的命令行参数,即staticvoidMain()或staticvoidMain(string[]args),后者接受命令行参数.一个C#程序中只能有一个Main()函数入口点.其他形式的参数不具有入口点语义,C#不推荐通过其他参数形式重载Main()函数,这会引起编译警告.

6.

其他形式的返回值不Main()函数返回值只能为void(无类型)或int(整数类型).具有入口点语义.

我们再来看"

HelloWorld.cs"

程序中Main()函数的内部实现.前面提过,Console是在命名空间System下的一个类,它表示我们通常打交道的控制台.而我们这里是调用其静态方法WriteLine().如同C++一样,静态方法允许我们直接作用于类而非实例对象.WriteLine()函数接受字符串类型的参数"

并把它送入控制台显示.如前所述,C#没有自己的语言类库,它直接获取Microsoft.NET系统类库.我们这里正是通过获取Microsoft.NET系统类库中的System.Console.WriteLine()来完成我们想要的控制台输出操作.这样我们便完成了"

程序.但事情远没那么简单!

在我们编译输出执行程序的同时,Microsoft.NET底层的诸多机制却在暗地里涌动,要想体验C#的锐利,我们没有理由忽视其背靠的Microsoft.NET平台.实际上如果没有Microsoft.NET平台,我们很难再说C#有何锐利之处.我们先来看我们对"

文件用csc.exe命令编译后发生了什么.是的,我们得到了HelloWorld.exe文件.但那仅仅是事情的表象,实际上那个HelloWorld.exe根本不是一个可执行文件!

那它是什么?

又为什么能够执行?

好的,下面正是回答这些问题的地方.首先,编译输出的HelloWorld.exe是一个由中间语言(IL),元数据(Metadata)和一个额外的被编译器添加的目标平台的标准可执行文件头(比如Win32平台就是加了一个标准Win32可执行文件头)组成的PE(portableexecutable,可移植执行体)文件,而不是传统的二进制可执行文件--虽然他们有着相同的扩展名.中间语言是一组独立于CPU的指令集,它可以被即时编译器Jitter翻译成目标平台的本地代码.中间语言代码使得所有Microsoft.NET平台的高级语言C#,VB.NET,VC.NET等得以平台独立,以及语言之间实现互操作.元数据是一个内嵌于PE文件的表的集合.元数据描述了代码中的数据类型等一些通用语言运行时(CommonLanguageRuntime)需要在代码执行时知道的信息.元数据使得.NET应用程序代码具备自描述特性,提供了类型安全保障,这在以前需要额外的类型库或接口定义语言(InterfaceDefinitionLanguage,简称IDL).这样的解释可能还是有点让人困惑,那么我们来实际的解剖一下这个PE文件.我们采用的工具是.NETSDKBeta2自带的ildasm.exe,它可以帮助我们提取PE文件中的有关数据.我们键入命令"

ildasm/output:

HelloWorld.ilHelloWorld.exe"

一般可以得到两个输出文件:

helloworld.il和helloworld.res.其中后者是提取的资源文件,

我们暂且不管,我们来看helloworld.il文件.我们用"

程序打开可以看到元数据和中间语言(IL)代码,由于篇幅关系,我们只将其中的中间语言代码提取出来列于下面,有关元数据的表项我们暂且不谈:

classprivateautoansibeforefieldinitHelloWorldextends[mscorlib]System.Object{.methodpublichidebysigstaticvoid{.entrypoint//Codesize.maxstack8IL_0000:

IL_0005:

IL_000a:

ldstrcallret"

void[mscorlib]System.Console:

:

WriteLine(string)11(0xb)Main()cilmanaged

}//endofmethodHelloWorld:

Main.methodpublichidebysigspecialnamertspecialnameinstancevoid{//Codesize.maxstack8IL_0000:

IL_0001:

IL_0006:

ldarg.0callretinstancevoid[mscorlib]System.Object:

.ctor()7(0x7).ctor()cilmanaged

.ctor}//endofclassHelloWorld我们粗略的感受是它很类似于早先的汇编语言,但它具有了对象定义和操作的功能.我们可以看到它定义并实现了一个继承自System.Object的HelloWorld类及两个函数:

其中可在Main()和.ctor()..ctor()是HelloWorld类的构造函数,"

源代码中我们并没有定义构造函数呀--是的,我们没有定义构造函数,但C#的编译器为我们添加了它.你还可以看到C#编译器也强制HelloWorld类继承System.Object类,虽然这个我们也没有指定.关于这些高级话题我们将在以后的讲座中予以剖析.

那么PE文件是怎么执行的呢?

下面是一个典型的C#/.NET应用程序的执行过程:

1.用户执行编译器输出的应用程序(PE文件),操作系统载入PE文件,以及其他的DLL(.NET动态连接库).2.操作系统装载器根据前面PE文件中的可执行文件头跳转到程序的入口点.显然,操作系统并不能执行中间语言,该入口点也被设计为跳转到mscoree.dll.NET(平台的核心支持DLL)的_CorExeMain()函数入口.3.CorExeMain()函数开始执行PE文件中的中间语言代码.这里的执行的意思是通用语言运行时按照调用的对象方法为单位,用即时编译器将中间语言编译成本地机二进制代码,执行并根据需要存于机器缓存.4.5.程序的执行过程中,垃圾收集器负责内存的分配,释放等管理功能.程序执行完毕,操作系统卸载应用程序.

清楚的知晓编译输出的PE文件的执行过程是深度掌握C#语言编程的关键,这种过程的本身就诠释着C#语言的高级内核机制以及其背后Microsoft.NET平台种种诡秘的性质.一个"

程序的概括力已经足够,在我们对C#语言有了一个很好的起点之后,下面的专题会和大家一起领略C#基础语言,窥探Microsoft.NET平台构造,步步体验C#锐利编程的极乐世界,Let'

sgo!

返回页首第二讲第二讲C#语言基础介绍在体验C#的锐利之前,关乎语言基本知识的掌握是必不可少的一环.由于C#基本语言很多源自C/C++,在这里对那些和C/C++类似的地方仅作简单介绍,我们将体验专注于那些区别于传统C/C++的关键的语言基础知识.数据类型C#语言的数据类型主要分为两类:

值类型和引用类型.另外一种数据类型"

指针"

是为其中unsafe上下文指对代码进行unsafe标示以满足unsafe上下文编程专门设定的,利用指针对内存直接进行操作要求的C#非托管代码,这些代码将失去Microsoft.NET平台的垃圾收集等CLR性质,我们放在"

COM互操作非托管编程与异常处理"

专题里

阐述.值类型的变量本身包含他们的数据,而引用类型的变量包含的是指向包含数据的内存块的引用或者叫句柄.从下面这幅图中可以清晰地看出两者的差别:

引用类型带来的可能的问题便是当多个变量引用同样的内存块时,对任何一个引用变量的修改都会导致该对象的值的改变.null值表示引用类型没有对任何实际地址进行引用.值类型可分为结构类型和枚举类型.结构类型包括简单类型和用户自定义结构类型.枚举类型和用户自定义结构类型我们将在"

第九讲结构,枚举,数组与字符串"

专题里详细阐述.简单类型又可分为布尔类型和数值类型.C#语言中布尔类型严格与数值类型区分,只有true和false两种取值,不存在像C/C++里那样和其他类型之间的转换.数值类型包括整值,浮点和decimal三种类型.整值类型有sbyte,byte,short,ushort,int,uint,long,ulong,char共九种.除了char类型外,其他8种两两一组分别为有符号和无符号两种.浮点值有float和double两种.decimal主要用于金融,货币等对精度要求比较高的计算环境.下表是对这些简单类型的一个详细的描述:

简单类型描述sbyteshortintlongbyteushortuintulong8-bit有符号整数16-bit有符号整数32-bit有符号整数64-bit有符号整数8-bit无符号整数16-bit无符号整数32-bit无符号整数64-bit无符号整数示例sbyteval=12;

shortval=12;

intval=12;

longval1=12;

longval2=34L;

byteval1=12;

byteval2=34U;

ushortval1=12;

ushortval2=34U;

uintval1=12;

uintval2=34U;

ulongval1=12;

ulongval2=34U;

ulongval3=56L;

ulongval4=78UL;

floatval=1.23F;

float

32-bit单精度浮点数

double

64-bit双精度浮点数

doubleval1=1.23;

doubleval2=4.56D;

boolval1=true;

boolval2=false;

charval='

h'

;

boolchar

布尔类型字符类型,Unicode编码28个有效数字的128-bit十进制类型

decimal

decimalval=1.23M;

引用类型共分四种类型:

类,接口,数组,委派.类除了我们可以定义自己的类型外,又包括两个比较特殊的类型object和string.object是C#中所有类型(包括所有的值类型和引用类型)的继承的根类.string类型是一个密封类型(不能被继承),其实例表示Unicode字符串,它和数组类型我们将放在"

第九讲结构,枚举,数组与字符串"

中详述.接口类型定义一个方法的合同,我们将在"

第七讲接口继承与多态"

中讲述.委派类型是一个指向静态或实例方法的签名,类似于C/C++中的函数指针,将在"

第八讲委派与事件"

中讲述.实际上我们将从后面的专题中看到这些类型都是类的某种形式的包装.每种数据类型都有对应的缺省值.数值类型的缺省值为0或0.0,其中char的缺省为'

\x0000'

.布尔类型的缺省值为false.枚举类型的缺省值为0.结构类型的缺省值是将它所有的值类型的域设置为对应值类型的缺省值,将其引用类型的域设置为null.所有引用类型的缺省值为null.不同类型的数据之间可以转换,C#的类型转换有隐含转换,明晰转换,标准转换,自定义转换共四种方式.隐含转换与明晰转换和C++里一样,数据从"

小类型"

到"

大类型"

的转换时为隐含转换,从"

大类型"

的转换为明晰转换,明晰转换需要如"

(Type)data"

一般的括号转换操作符.标准转换和自定义转换是针对系统内建转换和用户定义的转换而言的,两者都是对类或结构这样的自定义类型而言的.变量与常量变量表示存储位置,变量必须有确定的数据类型.C#的类型安全的含义之一就是确保变量的存储位置容纳着合适的类型.可以将C#中的变量分为静态变量,实例变量,传

值参数,引用参数,输出参数,数组参数和本地变量共七种.本地变量则是在方法体内的临时变量.静态变量和实例变量主要是针对类或结构内的数据成员(又叫域)而言的.静态变量在它寄存的类或结构类型被装载后得到存储空间,如果没有对它进行初始化赋值,静态变量的初始值将是它的类型所持有的缺省值.实例变量在它的类实例被创建后获得存储空间,如果没有经过初始化赋值,它的初始值与静态变量的定义相同.两者更详细的说明我们放在"

第六讲域方法属性与索引器"

专题里.传值参数,引用参数,输出参数,数组参数主要针对方法的参数类型而言的.简单的讲传值参数是对变量的值的一种传递,方法内对变量的改变在方法体外不起作用.对于传值参数本身是引用型的变量稍有不同,方法内对该引用(句柄)变量指向的数据成员即实际内存块的改变将在方法体外仍然保留改变,但对于引用(句柄)本身的改变不起作用.引用参数是对变量的句柄的一种传递,方法内对该变量的任何改变都将在方法体外保留.输出参数是C#专门为有多个返回值的方法而量身定做的,它类似于引用变量,但可以在进入方法体之前不进行初始化,而其他的参数在进入方法体内C#都要求明确的初始化.数组参数是为传递大量的数组元素而专门设计的,它从本质上讲是一种引用型变量的传值参数.它们更详细的阐述我们也放在"

专题里.本地变量严格的讲是在C#的块语句,for语句,switch语句,using语句内声明的变量,它的生命周期严格地被限制在这些语句块内部.常量在编译时便确定它的值,在整个程序中也不许修改.常量声明的同时必须赋值.由于它的编译时确定值的特性,引用类型可能的值只能为string和null(除string外,引用类型的构建器必须在运行时才能确定引用类型的值).操作符与表达式C#保留了C++所有的操作符,其中指针操作符(*和->

)与引用操作符(&

)需要有unsafe的上下文.C#摈弃了范围辨析操作符(:

),一律改为单点操作符(.).我们不再阐述那些保留的C++的操作符,这里主要介绍C#引入的具有特殊意义的几个操作符:

as,is,new,typeof,sizeof,stackalloc.as操作符用于执行兼容类型之间的转换,当转换失败时,as操作符结果为null.is操作符用于检查对象的运行时类型是否与给定类型兼容,当表达式非null且可以转化为

指定类型时,is操作符结果为true,否则为false.as和is操作符是基于同样的类型鉴别和转换而设计的,两者有相似的应用场合.实际上expressionastype相当于expressionistype?

(type)expression:

(type)null.作为操作符的new用于在堆上创建对象和调用构造函数,值得注意的是值类型对象(例如结构)是在堆栈上创建的,而引用类型对象(例如类)是在堆上创建的.new也用于修饰符,用于隐藏基类成员的继承成员.为隐藏继承的成员,使用相同名称在派生类中声明该成员并用new修饰符修改它.typeof运算符用于获得某一类型的System.Type对象,我们将在"

第十讲特征与映射"

里结合Microsoft.NET的类型系统对它作详细的阐述.sizeof运算符用于获得值类型(不适用于引用类型)的大小(以字节为单位).stackalloc用于在堆栈上分配内存块,仅在局部变量的初始值设定项中有效,类似于C/C++语言的_alloca.sizeof和statckalloc都由于涉及内存的直接操作而需要unsafe上下文.操作符重载使得自定义类型(类或结构)C#里的某些操作符可以像C++里那样被重载.可以用简单的操作符来方便的表达某些常用的操作.为完成一个计算结果的一系列操作符和操作数的组合称为表达式.和C++一样,C#的表达式可以分为赋值表达式和布尔表达式两种,C#没有引入新的表达式形式,我们对此不再赘述.命名空间与语句C#采用命名空间(namespace)来组织程序.命名空间可以嵌套.using指示符可以用来简化命名空间类型的引用.using指示符有两种用法."

语句可以使我们用简短的类型名"

来代替类型"

."

usingOutput=System.Console;

语句可以使我们用别名"

Output"

来代替类型"

.命名空间的引入大大简化了C#程序的组织方式.C#语句可以分为标号语句,声明语句,块语句,空语句,表达式语句,选择语句,反复语句,跳转语句,try语句,checked/unchecked语句,lock语句,using语句.标号语句主要为goto跳转设计,不允许跨方法的跳转,但允许小规模的方法内的跳C#转.声明语句可以同时进行初始化赋值,对象的实例化声明需要new关键字.块语句采用"

{"

和"

}"

定义语句块,主要是界定局部变量的作用范围.空语句在C#中用分号"

"

表示,没有执行语义.表达式语句通过表达式构成语句.

选择语句有if语句和switch语句两种,C++别无二致.与反复语句除了while,do,for三种循环结构外引入了foreach语句用于遍历集合中所有的元素,但这需要特定的接口支持,我们在后面的章节里对之作详细阐述.跳转语句有break,continue,goto,return,throw五种语句,前四种与C++里的语义相同,throw语句与后面的try语句我们将在"

第十一讲COM互操作非托管编程与异常处理"

阐述.checked/unchecked语句主要用于数值运算中溢出检查的上下文.lock语句主要用于线程信号量的锁控制.using语句主要用于片断资源管理.这些我们在后续章节里都会有具体的涉及.返回页首第三讲Microsoft.NET平台基础构造抛开Microsoft.NET平台去谈C#是没有意义的,C#之"

Sharp"

也正在其后端强大的平台.仅仅拘泥于语法层面是体验不了C#的锐利之处的,C#程序很多诡秘之处必须依靠Microsoft.NET平台才能深度的掌握和运用.简单的讲,Microsoft.NET平台是一个建立在开放互联网络协议和标准之上,采用新的工具和服务来满足人们的计算和通信需求的革命性的新型XMLWeb智能计算服务平台.它允许应用程序在因特网上方便快捷地互相通信,而不必关心使用何种操作系统和编程语言.从技术层面具体来说,Microsoft.NET平台主要包括两个内核,即通用语言运行时(CommonLanguageRuntime,简称CLR)和Microsoft.NET框架类库,它们为通用语言运行时是建立在操作系统最Microsoft.NET

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 党团工作 > 思想汇报心得体会

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1