非典型性C语言教程- 0.3 计算机程序到底是什么

来源:互联网 发布:机构交易软件 编辑:程序博客网 时间:2024/04/28 02:04

前几天上课又又听到了老师在宣扬“计算机行业没有经验”的论点。说计算机行业发展的太快,越老越不行,积累的经验转眼就过时。这种浮躁的言论已经听过无数次了,但是一个大学研究生课的老师在课堂上讲出来还是第一次。今天这个主题就和60年前计算机就出现的东西有关。

上次讲了,编译程序首先调用预处理程序处理C语言文件中的预处理命令,然后自己编译之生成目标文件,最后调用连接程序将目标文件和库文件连接成一个可执行程序。那么一段计算机程序到底是什么呢?

60年前阿兰.图灵,冯.诺依曼等人提出了计算机的体系模型,60年过去了目前实际运行的计算机都是注明的冯.诺依曼体系。首先讲图灵机的概念,下面是www.wikipedia.org 条目Turing machienes对通用图灵机的简介:

Turing machines are extremely basic abstract symbol-manipulating devices which, despite their simplicity, can be adapted to simulate the logic of any computer that could possibly be constructed. They were described in 1936 by Alan Turing. Though they were intended to be technically feasible, Turing machines were not meant to be a practical computing technology, but a thought experiment about the limits of mechanical computation; thus they were not actually constructed. Studying their abstract properties yields many insights into computer science and complexity theory.

A Turing machine that is able to simulate any other Turing machine is called a Universal Turing machine (UTM, or simply a universal machine). A more mathematically-oriented definition with a similar "universal" nature was introduced by Alonzo Church, whose work on lambda calculus intertwined with Turing's in a formal theory of computation known as the Church–Turing thesis. The thesis states that Turing machines indeed capture the informal notion of effective method in logic and mathematics, and provide a precise definition of an algorithm or 'mechanical procedure'.

这个条目有图灵机的形式化定义,以及关于图灵机几个著名问题的证明。简单来说图灵机由4部分构成:
  1. 一条无限长的纸带,分为一个一个单元,这条纸带可以左右移动。每个单元可以记录符号。
  2. 一个头,可以在纸带上读和写符号。
  3. 活动表,记录了纸带和头如何活动。
  4. 一个状态寄存器,记录活动表的状态。
图灵模仿了人解题的过程,解决一个问题时,头在根据活动表的内容读或写纸带单元的内容,并相应的移动纸带。这个模型就是现代计算机的鼻祖。后来冯.诺依曼提出了更具体的计算机体系。计算机由5部分组成:
  1. 执行单元
  2. 运算部件
  3. 内存
  4. I/O
  5. 程序计数器PC
执 行单元根据PC指示的地址去内存中读取指令,然后指令可以读写内存,将内存取出的数字交给运算部件运算。冯.诺依曼机器中指令和数据是同一存储的。人通过 I/O来与计算机交互。这个模型和图灵机基本类似:纸带就是内存,活动表也是内存的一部分,头就是执行和运算部件。程序就是活动表中左右移动纸带,读写纸 带的活动序列。同样本质上来讲程序就是内存中的指令序列。

后来编写程序的技术日新月异,各种概念技术层出不穷,但是本质上来说任何程序, 静态的如C, Forturn,Pascal,稍微动态一点的C++,Java,动态的Python, Lua,Ruby,传说中的 Lisp,Prolog最终都是内存中的指令序列。因为60年来计算机都是遵循冯.诺依曼模型的。

虽然人自己到底是怎么描述世界的还不是 很清楚,但是人描述世界的方式肯定和计算机描述世界的方式差别巨大,于是人们就不断的发展编程技术使得编程能更接近人描述世界的方式。首先是汇编。显然一 串数字是很不好记住的,于是用助记符去代表难以理解的数字。比如讲0xCC表示为int 3。后来发展出第一种高级语言Forturn。

60 年代人们发现单纯的跳转指令,使得程序很不好理解(人不好理解,机器一点问题没有),于是发展出结构化程序设计,使得调用子程序(很多名字过程,函数,方 法)有了标准。后来人们发现子程序一般要和程序处理的数据结合在一起,于是就发展了面向对象OO的技术。编译器自动完成在函数调用的时候传递this参 数,省去了自己写的麻烦。后来发现程序编译完成后,没有源代码就无法知道该怎么调用,于是加入元数据让编译完成之后的组建也能自己描述自己。

无论技术怎么更新,新技术只是自动的解决原来技术中不足的地方。比如用汇编照样可以写出面向对象的程序,但是用Java就方便的多,因为编译器帮你完成了许多工作,但是一个Java程序和一个汇编程序一样,最终执行的时候都是一条一条的计算机指令没有什么区比。

第0章说过,C语言重要的一条原因就是C语言最贴近计算机的模型。C语言由一组函数构成,函数就是一段一段的指令序列。函数中有一个叫main的,程序从main开始执行起,就是指令序列的起点。一直到结束,就是一个完成的指令序列。