程序并不是计算机程序设计中独有的概念,在日常生活中我们也常见到这个词,例如一个会议的日程、一场演出的节目单等,这些程序都是由人的一项项的活动组成的,身处其中时通常需要按部就班地一步步完成一系列动作,有序地完成每一项活动也就实现了程序的目标。可以说,对这种活动过程细节动作的描述就是一个“程序”。
日常生活中的程序性活动与计算机里的程序执行类似,这一点有助于我们理解计算机的工作方式。日常生活中的程序性活动里有更多变数,许多事情并不是完全按照程序做,可以有很大的灵活性,但是计算机对程序的执行是完全严格的。计算机的工作方式有两种,一种是交互式的,即人给机器一条指令,机器就完成一个操作;另外一种是程序自动控制式的,即把计算机要完成的操作用一条条指令按序排好,其中每条指令对应计算机执行的一个基本动作,计算机一步步执行了这个指令序列,也就完成了我们希望它做的事情,而且整个指令序列执行过程中不需要人来干预。为了解决某一特定问题而用某种程序设计语言编写的指令序列称为计算机程序或程序。在执行程序前必须先排好程序,排定以时间为进程必须完成的各种操作叫做程序设计或编程,程序设计的产品就是程序。
计算机是人们处理信息的一种重要工具,它在人的控制下,按照人的意志正确地工作。人给机器一条指令,机器就完成一个操作。如果把一系列指令输入计算机存储起来,计算机就能按照指令序列实现操作的自动化。为了与计算机交流,指挥计算机工作,就需要一种意义清晰、人使用起来方便、计算机能理解的描述方式。也就是说,需要一种适用的描述程序的语言。供人编写计算机程序的语言就是程序设计语言,也常称为编程语言。
当今使用的程序设计语言大致可以分为三类:机器语言、汇编语言和高级语言。
1. 机器语言
本质上计算机只能识别“0”和“1”这样的二进制信息,在计算机内部,一切信息都以二进制编码的形式存在,计算机存储并执行的程序也不例外。机器语言的程序全部由“0”和“1”表示出来,例如,一个16位的计算机,由16个二进制数组成一条指令,这些指令叫做机器指令。16个0和1可以组成2 16 个不同的指令或信息,这些指令的集合叫做机器语言。机器语言是计算机能直接识别和执行的唯一语言。用机器语言写出的程序称为机器语言程序。计算机刚诞生的时候,人们只能使用机器语言编写程序。下面的机器语言程序计算a、b的和并存储在c中:
0001000000001000
0001000100000101
0100000000000001
0001000000001100
人们用这种语言编写程序很不方便,非常繁琐,工作效率极低,写出的程序难于理解,不论是阅读程序还是调试程序都非常困难。另外,机器语言是与机器有关的,特定的机器语言只能用在特定的一类机器上,不是通用的。
2. 汇编语言
为了克服机器语言的缺点,人们用一些特殊的符号(即助记符)来表示机器指令,例如用ADD代表“加”,用SUB代表“减”。这些助记符的使用增加了一点汇编语言的可读性。汇编语言的语句与计算机硬件操作有一一对应关系,每种汇编语言都是支持这种汇编语言的计算机所独有的。用汇编语言写的程序需要专门的软件处理,翻译成机器语言后计算机才能执行。下面是用某种汇编语言编写的计算a、b和的程序:
LOAD a,4
LOAD b,5
ADD a, b
汇编语言出现后计算机的用途迅速扩大,但基本上有多少种计算机就有多少种汇编语言,因此汇编语言同机器语言一样也是面向机器的,通用性较差。尽管如此,汇编语言一直被人们所使用,主要是由于其执行速度快、占用存储空间小、对硬件操作灵活等特性。
3. 高级语言
为加速程序开发的进程,1954年人们创造出了第一个高级语言FORTRAN,宣告了程序设计的一个新时代的开始。FORTRAN采用了完全符号化的描述形式,用类似数学表达式的形式描述数据的计算。之后人们又提出了近千种语言,大部分为实验性语言,只有少数语言得到广泛应用。高级语言非常接近于人类的自然语言和数学语言,它的一个语句往往对应几条机器指令。用高级语言编写计算a、b的和并存储在c中的语句如下:
c=a+b;
一般来说,高级语言不再是面向机器的了,而是面向过程的语言,即把解题过程的每一步用计算机语言的语句描述出来,再配上适当的语言处理程序,计算机就能执行。因此,这种语言也称“算法语言”。高级语言有很多种,如FORTRAN、BASIC、Pascal、C、C++、Java等,不管是哪种高级语言源程序都必须经过相应的语言处理程序翻译成机器指令才能执行。
在用高级语言进行程序设计时要注意以下三个概念:
1)语法:每种程序设计语言都有自己的语法规则,这些规则是非常严格的。在进行编译时系统会按语法规则严格检查程序,如有不符合语法规则的地方,计算机会显示语法有错信息。
2)语义:某一语法成分的含义。例如,C语言中用“int”定义整型变量,用“char”定义字符型变量,用“while”语句实现循环,用“+”表示加法,用“!=”表示不等运算,等等。在使用时必须了解每一种语法成分的正确含义。
3)语用:正确使用语言。要善于利用语法规则中的有关规定和语法成分的含义有效地组成程序以达到特定的目的。
要把一个编好的源程序上机实现,除了需要一定的硬件环境外,还需要软件的支持。首先看一下高级语言源程序实现的步骤。
图1-1表示了程序运行的过程,可以看出程序运行必须经过编辑-编译-连接-运行四个阶段。
图1-1 高级语言程序实现的步骤
(1)编辑
输入源程序是程序实现的第一步。计算机系统为用户提供了编辑程序,利用编辑程序可以输入源程序并对它进行修改。修改完的程序存放在磁盘上,以后需要时再调入计算机进行编译。
(2)编译
C语言属于高级语言,它的语法规则与汇编语言和机器语言相比更接近人类自然语言的习惯。但是,计算机能够“看”懂的唯一语言是机器指令。所以,当我们要让计算机“看”懂一个C程序时,就必须使用一种叫做“编译器”的工具,将这个C程序“翻译”成计算机能理解的机器指令。
(3)连接
经过编译程序得到的目标程序是不能直接执行的(因为目标程序可能调用内部函数、外部函数、系统提供的过程库中的程序),或者一个程序有若干个程序段(子程序)是分别编译的,它们排放的先后次序与实际执行次序不一致,编译程序无法知道先执行谁后执行谁,因此需要由连接程序将所有的目标程序和系统提供的库函数、过程库等连接在一起成为一个整体,形成可执行程序。
(4)运行
在编译和连接工作成功地完成之后可以得到可执行程序,将它调入内存即可执行。
在编译和连接过程中,如果出现错误,就要修改程序,重新进行编译和连接。运行可执行程序,如果程序的运行结果不是我们所期望的,说明源程序文件中存在着错误。可以使用调试器对可执行程序进行跟踪调试来查找错误发生的原因。
将高级语言源程序翻译成等价的机器代码的方式有两种,即编译方式和解释方式,相应的程序也有编译程序和解释程序:
· 编译程序:编译程序的主要功能是将高级语言程序翻译成机器语言程序,另外它还包含查错的功能。在翻译过程中如果发现程序有错,则不生成目标程序,并向用户报告出错信息。用户必须重新调用编辑程序修改源程序,然后再次进行编译,直到无错为止,这时产生目标程序。一般高级语言如C、PASCAL、FORTRAN都采用编译方式。编译方式速度快、占用内存少。
· 解释程序:解释程序也将高级语言源程序翻译成机器代码,与编译程序不同的是它是边翻译边执行,翻译一句执行一句,不产生整个程序的目标程序,当再次运行该程序时还要重复翻译的过程,所以解释方式效率低、执行时间长、占用内存多,但使用灵活方便。早期的BASIC语言采用的就是解释方式。
C语言是国际上公认的最重要的通用程序设计语言之一。它既可以用来写系统软件,也可以用来写应用软件。
早期的系统程序设计使用的是汇编语言,这主要是因为汇编语言最能够体现计算机硬件指令集的特性,其表达能力足以描述系统设计的各个方面的特性,且由汇编语言程序生成的代码有较高的质量。但是,汇编语言程序的可读性、可移植性都比较差。能否推出一种语言,它既向下靠拢汇编语言,使用户能接近硬件,且生成的代码有较高的质量,又向上靠拢高级语言,使程序具有较好的可读性和可移植性呢?世界上很多杰出的科学家对这一问题作了尝试,其中美国贝尔实验室的D.M.Richie和K.Thompson的研究成果尤为出色。
1970年K.Thompson以剑桥大学Richards教授的BCPL语言为基础,设计出了简单而且接近硬件的B语言,并用B语言写了第一个UNIX操作系统,在PDP-7上实现。1971年,又在PDP-11/20上实现了B语言,并写了操作系统。但B语言采用字编址,不能适应PDP-11用字节编址进行存取的要求,另外B语言缺少具有一定表达能力的数据类型,而且生成的是解释性的执行代码,执行速度慢。这些使B语言的使用有一定困难。
贝尔实验室的D.M.Richie与K.Thompson一起从事UNIX操作系统的开发工作,1972年~1973年Richie在B语言基础上开发了C语言,1973年用C语言改写了UNIX操作系统的大部分代码,加进了多道程序功能,使UNIX发生了本质变化。从20世纪70年代中期开始,UNIX和它所支持的C语言在贝尔实验室内部和大学里得到了普遍使用,特别是在1978年Prentice-Hall Inc.出版了由Brian W.Kernighan和D.M.Richie发表的世界上第一本有关C语言的专著《The C Programming Language》后,C语言的发展进入了一个崭新的阶段。
C在各种不同类型计算机上的普遍使用导致了许多不一致,它们虽然功能相似,但通常互不兼容。对需要为不同平台编写可移植程序的开发人员,这是个严重的问题。1983年,美国国家标准化协会(ANSI)根据C语言问世以来的各种版本对C的发展和扩充,制定了新的标准,称为ANSI C。1989年,ANSI公布了新标准ANSI C 89,这个标准被国际化标准组织所接受,C语言的设计者Kernighan和Richie合著的《The C Programming Language, Second Edition》介绍了ANSI C的全部内容,是学习C语言的一部重要参考书。1999年,ANSI又公布了新标准ANSI C 99。