1700436375
BCPL(Basic Combined Programming Language,基本组合编程语言)是另一种用于系统级编程的语言。它由剑桥大学教授马丁·理查兹(Martin Richards)设计。理查兹1967年访问麻省理工学院时为它写了编译器。BCPL比PL/I的任何分支版本都简单得多,很适合编写操作系统代码。贝尔实验室Multics开发组成员们非常熟悉BCPL。
1700436376
1700436377
贝尔实验室退出Multics项目后,肯·汤普森认为,“没有Fortran,计算机就不完整”,于是他着手为PDP-7编写Fortran编译器。事实证明这太艰难了,因为PDP-7 Unix只有4K个18位字长(8 KB)的主存储器供编译器等用户程序使用。
1700436378
1700436379
肯不断重新设计,最终打造出满足PDP-7条件限制的语言。这种语言更接近于BCPL而不是Fortran,肯叫它B语言。1993年,丹尼斯·里奇在“The Development of the C Language”(C语言的开发)中阐述道:
1700436380
1700436381
“可以将B语言看作没有类型的C语言。更准确地说,它是压缩到8 KB内存中、再经汤普森的大脑过滤的BCPL。它的名字看上去比较像是BCPL的缩写。不过也有另一种说法,认为它来源于与B语言毫无相关的Bon语言,一种由汤普森在Multics时期创造的语言。Bon语言则要么是以他的妻子邦妮的名字命名,要么是(根据其手册中引用的一段百科全书)以某个宗教的名字命名。”
1700436382
1700436383
到目前为止,我们故事中的计算机都以字为操作单位,而不是以字节为操作单位。也就是说,它们的操作针对明显大于单个字节的块状信息。IBM 7090和类似的计算机,如GE系列,天然只能以36位(大约4字节)的块为单位来操纵信息;PDP-7的块单位是18位(大约2字节)。面向字的计算机在单独或按顺序处理字节时很笨拙:程序员必须使用库函数或通过特别的编程技巧来访问装在较大块中的单个字节。
1700436384
1700436385
相比之下,PDP-11以字节为操作单位:它主存储器的基本单位是8位字节,而不是早期计算机的18位或36位字长。它也可以处理较大块的信息,如16位和32位整数以及16位地址。
1700436386
1700436387
B语言很适合PDP-7这样以字为操作单位的计算机,但不适合PDP-11这样以字节为操作单位的计算机,所以,PDP-11到货后,丹尼斯开始针对新的架构对B语言进行增强,并为其编写编译器。新的语言被称为“NB”,即“New B”(意为“新B语言”),最后发展成了C语言。
1700436388
1700436389
B语言与C语言主要区别之一是,B语言无类型,而C语言则支持与PDP-11提供的数据类型相匹配的数据类型:1字节、2字节的整数,以及4字节或8字节的浮点数。在BCPL和B这样的语言中,指针(内存地址)和整数被同等看待。此前多年以来程序员们将它们当作相同大小的数据来处理,这样做不算明智,而C语言则正式将它们区别对待。
1700436390
1700436391
C语言支持对类型指针的算术运算,这是对编程语言的新颖贡献。指针是内存地址的值,标记主存储器中的某个位置。指针的类型即它指向对象的类型。在C语言中,如果该位置对应的是该特定类型对象的数组中的一个元素,那么,在指针上加1就会得到数组中下一个元素的地址。虽然乱用指针是破坏代码的“要诀”,但指针运算契合自然,正确使用的话,效果很好。
1700436392
1700436393
之前一段时间,人们已经清楚地认识到,Unix应该从汇编语言转换为更高层级的语言,而C语言正是上上之选。肯在1973年曾3次尝试用C语言编写内核,但直到丹尼斯在语言中加入了定义和处理嵌套数据结构的机制(struct)才得以实现。那时候,C语言已经有足够的表现力来编写操作系统代码,Unix也就成了主要用C语言编写的程序。第6版内核有大约9 000行C语言代码和大约700行汇编语言代码。汇编代码用于设置寄存器、设备和内存映射等与特定机型相关的操作。
1700436394
1700436395
第一份广泛传播的C语言说明书是《C程序设计语言》(The C Programing Language)(图4-5),这本书是我和丹尼斯在1978年出版的,第2版于1988年推出。
1700436396
1700436397
1700436398
1700436399
1700436400
图4-5 K&R书第1版的封面,1978年
1700436401
1700436402
我只浅尝过B语言。为了自娱,我写了一本教程,帮助别人学习。丹尼斯创造出C语言后,我没花多少工夫就把那本B语言教程修改成了C语言教程。事实证明,C语言教程很受欢迎。随着Unix和C语言的传播,我觉得值得专门写一本关于C语言的书。我不假思索就去问丹尼斯是否愿意一起写。一开始他可能不太情愿,但我百般游说,最终他同意了。邀请丹尼斯一起写这本书是我在技术生涯中做过的最聪明或者说最幸运的事情——因为丹尼斯是合著者的缘故,该书尤显权威,而且我也就能在书里引用他的参考手册了。
1700436403
1700436404
我写了大部分教程章节的初稿,丹尼斯写了系统调用那章,当然他也提供了参考手册。我们互相帮忙审订,成品融合了两个人的写作风格,但参考手册几乎完全保持原状,充分体现了丹尼斯的写作风格。如比尔·普劳格所言,丹尼斯描述C语言时,“一针见血”。参考手册就像C语言本身一样:精准、优雅、紧凑。
1700436405
1700436406
1989年,ANSI和ISO完成了第一份C语言正式标准。这份标准对语言的描述直接基于丹尼斯的参考手册。丹尼斯在标准制定的早期阶段就介入了。作为C语言的创造者,他的意见举足轻重,足以否决个别太过糟糕的提案。
1700436407
1700436408
C语言很重要,但它对标准库的使用也很重要。标准库为程序员提供了进行格式化输入和输出、字符串处理和数学函数等操作所需的基础能力。C语言自带规模适中的函数库,这样程序员在编写新程序时就不需要重新发明每个例程。
1700436409
1700436410
其中,最大的库组件提供了格式化输出能力。今天,C语言的printf函数已经为许多其他语言所采用,每位程序员都对它耳熟能详。迈克尔·莱斯克的可移植I/O包写于1972年,目的是让程序能够很容易地移植到Unix,或从Unix移植到其他系统。它包含了printf的首个版本,以及用于解析格式化输入的scanf。这些程序包经过重新设计,放到了C语言编译器中。
1700436411
1700436412
虽然printf和scanf后来做了扩展,但核心转换功能和70年代初没有区别,库中的大部分其他函数也能正常工作。今天,标准库和语言规格说明本身一样,都是C语言标准的一部分。
1700436413
1700436414
将C语言与其他语言进行对比很有意思。例如,在Fortran和Pascal中,输入和输出是语言的一部分,有特殊的语法来读写数据。其他一些语言不包含输入或输出,同时也不提供标准库,这可能是最不令人满意的选择。
1700436415
1700436416
C语言一直非常成功,是有史以来使用最广泛的语言之一。虽然它最初在PDP-11 Unix上诞生,但已经传播到了差不多每一款计算机上。正如丹尼斯在1993年提交到第二届编程语言史(History of Programming Languages)大会的论文中所说:
1700436417
1700436418
“C语言既古怪又有缺点,却获得了巨大的成功。虽然历史上的意外事件肯定有帮助,但C语言显然满足了人们对一种系统实现语言的需求,这种语言需要足够高效,足以取代汇编语言,但又足够抽象和流畅,足以描述各种环境下的算法和交互。”
1700436419
1700436420
当然,编程语言为数甚多,各有各的支持者与抨击者。C语言也会受到批评。然而,它仍然是计算领域的核心语言。在流行度、影响力和重要性的榜单上,它几乎总是名列前两、三位。在我看来,没有任何一种其他语言能在优雅度、表现力、效率和简洁之间做到同样程度的平衡。C语言还启发了许多其他语言的基础语法,其中就有C++、Java、JavaScript、awk和Go。它做出了极具影响力的贡献。
1700436421
1700436422
1700436423
1700436424
[
上一页 ]
[ :1.700436375e+09 ]
[
下一页 ]