描述的层次和计算机系统

描述的层次

哥德尔串G和巴赫的赋格曲都有这样一个性质:能在不同的层次上被理解。我们都熟悉这种事情。有时我们也会被搞糊涂,而另一些时候还是能毫无困难地掌握它们。例如,我们都知道人体是由大量的细胞所组成(大约有二十五万亿个),因此我们所做的一切原则上都能在细胞水平上被描述。或者说它们甚至可以在分子水平上被描述。大多数人都把这作为一个事实而接受了。我们去找医生看病,医生对我们的观察层次就要低于我们自我观察的层次。我们可以一边读着关于DNA和”遗传工程”的文章,一边呷着咖啡。我们似乎调和了这样一些关于我们自身的极不相同的图像,其实我们只不过是不把它们联系在一起。我们几乎无法把关于我们自身的微观描述和我们的自我感觉联系起来,因此我们很可能是把关于我们自身的不同表示存储在我们心智的不同”格子”中了。我们几乎从不在这些概念之间转来转去,纳闷”这两种完全不同的东西怎么可能是同一个我呢?”

在看电视的时候,屏幕上一连串画面显示着卓别林在跑来跑去,这时,我们知道事实上我们看到的不是一个人,而是平面上闪烁的一片光点。我们知道这一点,但这是埋藏在思想深处的。关于屏幕上的东西,我们有两个尖锐对立的表示,但这不会给我们造成麻烦。我们可以对其中之一置之不理,而去注意另一个------这是我们大家都用的办法。哪一个”更真实些”?这取决于你是一个人,还是一只猫、一台计算机、或一架电视机。

组块化与棋术

人工智能研究中的一个重大问题,就是要指出如何跨越这两种描述间的鸿沟,即如何构造一个系统,使它可以接收一个层次上的描述,然后从中生成另一个层次上的描述。通过探索如何给计算机编制一个好的下棋程序,这条鸿沟在人工智能中明确地表现出来了。以前人们认为------在50年代和60年代------让机器下一手好棋的关键,是使它在可能的着法序列构成的分支网络上,比任何棋术大师所能超前搜索的步数都多。可是,当这一目标逐渐达到后,计算机的棋艺并没有突飞猛进,超过人类高手的水平。事实上,一个高手在和当今最好的下棋程序对局时仍可以稳操胜券。1

这种现象的原因实际上已讨论了许多年。在40年代,荷兰心理学家阿德里安·德·格鲁特就研究了下棋时新手和大师是怎样感知一个棋局的。用那些刻板的术语来说,他的研究结果指出大师们是以”组块”来感知棋子的分布的。有一种比直接描述每处棋子的位置层次更高的棋局描述,而大师就是以某种方式生成了这样一个棋局的心智表象。这一点已被下述事实所证实:两个人都用五秒钟时间审视棋盘之后,大师能很快地重新摆出一盘实际对局中的某个局面,而新手则要慢得多。下面这一事实是非常说明问题的:再现一个棋局时,大师们的错误涉及到把整整一组棋子放在错误的位置上,这几乎不改变对局的战略态势,但这在新手的眼里却是完全不同局面。一个决定性的事实是,在做同一个实验时,如果把棋子乱放在棋盘中的各个位置上,而不是取材于一个实际对局那么在重现这样一个随机局面的过程中,大师比新手也强不了多少。

结论是这样的:在正常的对局过程中,会有某种多次再现的局面------也就是某种模式------而大师正是对这种高层次的模式十分敏感。他和新手在不同的层次上思考,他们的概念集是不同的。几乎出乎所有人意料的发现是,大师在超前搜索时很少比新手走得更远------更有甚者,大师往往只检查屈指可数的几种可能着法!关键在于,他感知棋局的方式像一个过滤器:在观察局势时他实际上看不见坏棋------正像业余棋手在观察局势时看不见不合规则的棋步一样。任何懂一点棋术的人都已经对他的感知进行了组织,斜着走车、象走日字这样的着法不会出现在脑子里。类似地,大师级的棋手在观察棋局时已经建立了更高层次的组织,因此对他们来说,坏棋一般不会被想出来,就像对大多数人来说不合规则的棋不会被想出来一样。这可以称作对由各种可能性组成的巨大的树形结构所做的”隐式修剪”。相反,“显式修剪”是指先考虑一步棋,粗略地检查一番后,决定不再继续做进一步的检验。

这种区分同样适合于其它智力活动------例如作数学题。一个有才华的数学家往往不像庸才们所做的那样,考虑并尝试所有的错误途径,以达到所需的定理。相反,他一下就”嗅出”了有希望的途径,然后立即进行下去。

仅仅依赖于超前搜索的计算机下棋程序还没有被教会在一个更高的层次上思考,它的战略只是凭一股蛮劲进行超前搜索,企图压倒各种类型的对手。但这种办法并不灵。也许有一天,一个蛮劲足够大的超前搜索程序确实战胜了人类最好的棋手------但那也只是一个很小的智慧之果。因为我们已经揭示出了:智能紧密地依赖于为复杂的对象------如棋盘、电视屏幕、书页或画面------构造高层描述的能力。

相似的层次

通常,我们在理解一个情景时并不需要同时在头脑中容纳一个以上的层次,而且对同一个系统的不同描述一般在概念上相距甚远,就像我们前面提到过的一样。因此同时保存它们并不困难,只须把它们保存在心智世界中的不同区域里就行了。真正造成混乱的是这样一种情况:同一个系统允许两种以上不同层次的描述,而这些描述在某些方面又是彼此相似的。那时我们会发现,在考虑这种系统时,我们难以避免把层次搞混,很容易完全迷失方向。

毫无疑问,这种情况会发生。在我们考虑我们自己的心理的时候------例如,当我们试图理解人们从事各种活动的动机时------就是如此。在人的心智结构中有许多层次------当然对这个系统我们还没有很好地理解。但是,仍有上百种相互竞争的理论在说明人类行为的原因。每种理论都基于某种潜在的假设,关系到在寻找各种心理的”力”时,应当深入到这种层次结构的哪一层。由于目前我们差不多是用同一种语言描述所有的心智层次,这显然就造成了大量的层次混淆和许多错误的理论。例如,我们谈论”驱力”------但不知道这些驱力在人的心智结构中出自何处。我不想就此进一步讨论,只想说明我们进行自我认识时的混乱与下述事实有关:我们是由许多层次构成的,同时我们用重叠的语言在所有这些层次上描述我们自己。

计算机系统

在另一个领域中也有这样的情况:对同一个系统有许多层次的描述共存,而且这些层次在概念上彼此非常接近。我这里指的是计算机系统。当一个计算机程序在运行的时候,可以在若干个层次上观察它。在每一层上,描述都是用计算机科学的语言给出的,这使得所有这些描述都多多少少地彼此相似------然而不同的层次上得到的见解仍然极其不同。在最低层,描述会复杂得就像对电视屏幕上光点的描述一样。但就某些目的而言,这是最重要的视角。在最高层,描述极大程度地组块化,给人一种完全不同的感觉,尽管事实上许多概念都是最低层和最高层所共有的。高层描述中的组块类似于棋术大师的组块,也类似于屏幕图像的组块化描述:它们以简略的形式概括了若干在低层看来是不同的东西(见图57)。我们还是先别把事情搞得太抽象,先看看有关计算机的一些具体事实吧。我们来简述一下从最低层看计算机系统是什么样的。最低层?严格地说并不是,因为我没打算谈及基本粒子------但这里要谈到的是我们所愿意考虑的最低层。

图57."组块化"的想法

把一组对象当作一个”块”后,可以把它们看成一个单位。其边界有点像细胞膜或国境线:它使得其内部的那一组对象构成一个独立的单位。根据不同的需要,可以考虑组块的内部结构,也可以不考虑。

计算机的基本成分有”存储器”、“中央处理器”(CPU)以及一些”输入输出(I/O)设备”。首先我们来谈谈存储器。存储器被分为若干称为”字”的物理上分离的单元。为了描述得具体一些,我们假设存储器共有65536个字(这是个特殊的数,2的16次方)。一个字可以进一步分为我们当作计算机科学的原子的东西------“位”。

一个典型的字中大概有36位左右。2

image

------一个36位的字------

从物理上看,一个位不过是一种磁性”开关”,它可以处于两种状态。你不妨把这两种状态称为”开”和”关”,或”X”和”O”,或”1”和”0”…第三种是最常用的。这种表示很方便,但也可能使人误解,以为计算机说到底是存储数字的。这是错的。三十六个位组成的集合不一定要被想象成数字,正像一角钱不一定要被想象成一根冰棍的价格。钱可以有各种不同的用途,这取决你怎样使用它。同样,存储器中的一个字也可以有不同的功能。当然,有时这36位确实是表示了一个二进制数。另一些时候它们也可能是表示一个电视屏幕上的36个点,或文章中的一个词。存储器中的一个字应当如何理解,这完全取决于这个字在程序中所扮演的角色。当然,它也可能扮演多种角色------像卡农曲中的一个音符一样。

指令和数据

有一种对于字的解释我还没有提到,这就是”指令”。存储器中的字里面不仅可以放被处理的数据,还可以放一些作用于数据之上的程序。有那么一组有限的固定的操作,它们可以被中央处理器------CPU------所执行,而一个字的一部分,通常是前面的几位,可以被解释成要被执行的指令类型的名字。一个解释成指令的字的其余部分代表什么呢?最常见的是,它们说明要对存储器中的哪些字进行作用。换句话说,剩下的位构成了一个指向存储器中其它字的”指针”。在存储器中,每个字都有各自的位置,像大街上的房子一样。字的位置称为”地址”。存储器里可以有一条”街”或几条”街”------它们被称为”页”。因此,要寻找一个字的地址,必须知道它的页号(如果存储器是分页的)以及它在该页中的位置,所以指令的”指针”部分就是存储器中某个字(或某些字)的地址的数字化表示。对于指针是没有限制的,因此一条指令甚至可以”指向”它自己,这样当它被执行时,将造成对自身的某些修改。

在任一给定时刻,计算机怎样才能知道该执行什么指令呢?这记录在CPU里。有一个特殊的指针,指向要被解释成指令的下一个字(即存储着它的地址)。CPU把那个字从存储器中提取出来,通过电子手段把它复制到属于CPU自身的一个特殊的字中(CPU中的字通常不叫”字”,而叫”寄存器”)。然后CPU就执行这条指令。这条指令可以要求完成任意一种类型的操作。典型的操作包括:

ADD[加]:把指令中所指出的字加到一个寄存器上。(在这种情况下,所指出的字显然被解释成一个数字。)

PRINT[打印]:把指令所指出的字作为字母打印出来。(在这种情况下,这个字显然不是解释成一个数字,而是解释成一串字母。)

JUMP[转移]:转移到指令中所指出的字。(在这种情况下,告诉CPU把那个特定的字解释成它的下一条指令。)

除非指令明确要求其它作法,否则CPU将取出下一个字,并把它解释成指令。换句话说,CPU假定自己应当像个邮递员那样,沿着”大街”走下去,依次把一个个字解释成指令。但是这种顺序工作方式可以被像JUMP(转移)这样的指令所打破,还有一些指令也有这种效果。

机器语言之别于汇编语言

上面所说的只是”机器语言”的一个粗略框架。在这种语言中,所能执行的操作类型构成了一个不可扩展的有限集合。因此所有的程序,不管多大、多复杂,都必须用这几种类型的指令构成。看一个用机器语言写成的程序,差不多可以和一个原子一个原子地看一个DNA分子相比!翻回去看看图41,那个DNA分子的核苷酸序列------想想每个核苷酸都包含二三十个原子------再想象一下为一个微小的病毒(更不要说为人了!)一个原子一个原子地写出DNA------你就会体会到,用机器语言写一个复杂的程序是什么滋味,你也会体会到,在只能与程序的机器语言描述打交道的条件下去掌握程序的进展情况,那是一种什么滋味。

但必须提到的是,在计算机刚出现的时候,程序设计是在比机器语言更低的层次上(还有更低的层次!)完成的------即把导线彼此联接,因此恰当的操作都是通过”硬性联接”而实现的。这用现代标准来看简直原始得可怕,甚至想象一下都觉得苦不堪言。但毫无疑问,初次进行这种尝试的人们一定和现代计算机的先驱者们一样曾经感到非常振奋…

现在我们要上升到对程序进行描述的层次体系中较高的一层。这就是”汇编语言”层。汇编语言和机器语言之间差别并不大,事实上,这一改变很平缓。在汇编语言的指令和机器语言的指令之间实质上存在着一一对应。汇编语言的设计思想是要把各个机器语言的指令”组块化”,因此当你要用一条指令把一个数加到另一个数之上时,不必再写一个若干位组成的串”010111000”,而只写ADD(加)就行,然后也不必以二进制表示的形式给出地址,而是用一个”名字”指示存储器中的字。因此,用汇编语言写的程序很像用机器语言写的程序,只是容易被人读懂了。可以把用机器语言写的程序比作以晦涩的哥德尔配数法写成的一个TNT推导,而把用汇编语言写的同一程序比作以原始的TNT表示法写成的与之同构的TNT推导,后者当然比前者易懂多了。或者,回到关于DNA的想象上来,我们可以把机器语言和汇编语言之间的差别比作下面两种方法间的差别:一种是麻烦地一个原子一个原子地说明每个核苷酸,另一种是在说明一个核苷酸时仅仅给出它的名字(即”A”、“G”、“C”或”T”)。通过这种非常简单的”组块化”操作可以节约大量的劳动,虽然观念上并没有很大的改变。

翻译程序的程序

也许,汇编语言的主要意义不在于它与机器语言间并不显著的差别,而是这样一个关键的想法:程序完全可以在不同的层次上编制!想一想:硬件是被设计来”理解”机器语言写出的程序------即位序列------而不是面向字母和十进制数字的。把一个用汇编语言写的程序送进硬件会怎么样呢?这就像你想让一个细胞接受一片纸,上面的核苷酸序列是用字母写的,而不是作为一种化学构成物。细胞要一片纸有什么用呢?计算机要汇编语言写出的程序有什么用呢?

关键在这里:人们可以用机器语言写一个”翻译程序”。这个程序叫”汇编程序”,它可以接受易记的指令名、十进制数字及其它容易被程序员记住的方便的缩写,然后把它们转换成单调然而严格的位序列。用汇编语言书写的程序在被”汇编”(即翻译)之后,就可以”运行”了------或者说它的机器语言等价物可以运行了。但这只是个说法问题。哪个层次的程序在运行?如果你说是机器语言写出的程序在运行,那是绝不会错的,因为任何程序的运行都必须通过硬件------但根据汇编语言来考虑运行中的程序同样是很合理的。例如,你完全可以说”现在CPU正在执行JUMP(转移)指令”,而不是说”现在CPU正在执行’111010000’指令”。一个钢琴家在弹奏音符G-E-B-EGB时,也是在弹奏E小调和弦的一个琶音。没有理由排斥一个以高层次观点进行的事物描述。因此,可以把汇编语言写出的程序想象成与机器语言写出的程序在同时运行。我们对CPU正在做的事情有两种描述方式。

更高级的语言、编译程序和解释程序

靠计算机自己把程序从高层次翻译到低层次,这个强有力的想法在层次体系的更上一层得到了进一步贯彻。50年代初,人们用汇编语言编了几年程序之后,就认识到了一些有特点的结构往往反复出现在各种程序中。正像下棋一样,似乎存在某些基本的”定势”,它们会自然地出现在人们想要构造”算法”的时候------所谓”算法”是指人们对所要完成的操作过程的精确描述。换句话说,算法似乎有某些高层次的成分,用它们来描述操作过程,比用局限性很大的机器语言或汇编语言要容易得多,也漂亮得多。在典型情况下,一个算法的高层成分不只包含一两条机器语言指令,而是包含整整一组,并且这些指令在存储器中也不一定是相邻的。这样的一个成分可以在一个更高层的语言中用单个的项来表示------这就是一个组块。

除去标准组块------即新发现的那些可以构成所有算法的成分------之外,人们还认识到几乎所有的程序都包括有更大的组块------或者叫超组块。不同的程序有不同的超组块,这取决于程序要完成哪些高层次的任务。我们在第五章里已经讨论过超组块,用的是它们通常的称呼:“子程序”和”过程”。显而易见,对任何程序设计语言的一个强有力的扩充就是赋予它们下述能力:用已知的实体定义新的高层实体,然后用名字调用它们。这就把形成组块的运算直接建立在语言之中了。这样,就不再有一组固定的指令,要求所有的程序都直接用这组指令来编制,而是使程序员能构造自己的模块,每个模块都有自己的名字,而且可被用在程序内的任何地方,就像它们本来就是这种语言的成分一样。当然,这并没有超出下述事实:下到机器语言层,所有的事情仍是被同一组已有的机器语言指令所完成的,但它们对于处在高层的程序员来说不是明显可见的,它们是隐含的。

基于这种想法的新语言被称为”编译语言”。其中一种很早也很漂亮的叫做”Algol”,是”算法语言”的英文缩写。和汇编语言的情况不同,在Algol的语句和机器语言的指令之间不再有直接的一一对应。无疑,仍然有一种从Algol到机器语言的映射关系,但这要比汇编语言和机器语言间的关系”杂乱”得多。粗略地说,把Algol程序翻译成机器语言,有点像根据初等代数课本上的一道应用题列出方程式(事实上,从应用题转换到方程式要复杂得多,但这一比喻有助于体会把高级语言翻译成低级语言的过程中所必须完成的那些”清理”工作)。在50年代中期,称为”编译程序”的一些成功的程序被编制出来了,其功能就是完成从高级语言到机器语言的翻译。

“解释程序”也被发明出来了。像编译程序一样,解释程序也能把高级语言翻译成机器语言,但不是先把全部语句翻译完,然后执行机器代码,而是读一行然后立即执行它。这样做的优点是,使用者不必等写完一个程序后再使用解释程序。他可以一边一行一行地编,一边对它们进行检验。因此,如果把编译程序比作书面发言翻译,那么解释程序就可以被比作同声翻译。一种非常重要又很迷人的计算机语言是Lisp(“表处理”的英文缩写)。它是约翰·麦卡锡发明的,时间和Algol的发明时间差不多。从那以后,Lisp在人工智能研究人员中广泛地流行开了。

在解释程序和编译程序的工作方式之间有个很有趣的差别。编译程序先接收输入(如一个写好的Algol程序),然后产生输出(一个长长的机器语言指令序列)。至此,编译程序的任务就完成了,其输出就交给计算机去运行。与此相反,解释程序在程序员一条条地输入Lisp语句时一直在运行,每条语句马上被”就地执行”。但这并不是说每条语句是先翻译再执行的,那样的话一个解释程序就只是个一行一行进行处理的编译程序了。在解释程序中,下列操作是交织在一起的:读新的一行、“理解”它、执行它,它们同时进行。

解释程序的基本想法如下:每次新的一行Lisp语句输入,解释程序就设法处理它。这就是说解释程序开始工作,而且其中某些(机器语言的指令)被执行。当然,确切地说,执行哪一条指令,是取决于这个输入的Lisp语句的。在解释程序中有许多JUMP(转移)指令,因此新的一行Lisp可能使控制权以一种复杂的方式四处传递------向前,向后,再向前,等等。这样,每个Lisp语句都在解释程序中被转换成一条”路径”,沿着这条路径走就能得到所需的结果。

有时不妨把Lisp语句只看成一条条的数据,它们被连续地送入一个不停地运行的机器语言程序(即Lisp解释程序)。这样想往往是有帮助的,由此你会得到关于高级语言写出的程序和执行它的机器之间的关系的另一幅图像。

自举

当然,编译程序自身也是个程序,也必须用某种语言来书写。第一个编译程序是用汇编语言来书写的,而不是用机器语言,这样就可以充分利用已经建立在机器语言之上的初步成果。图58对这些复杂的概念进行了总结。

图58.汇编程序、编译程序与计算机语言的层次

汇编程序和编译程序都是用于向机器语言进行翻译的程序。这用直线表示。它们自身也是程序,开始时也需用某种语言写成。波浪线表示编译程序可以用汇编语言书写,汇编程序可以用机器语言书写。

随着复杂性的增长,人们认识到,一个部分完成了的编译程序可用于对其它部分进行编译。换句话说,一旦编译程序的核心部分写成了,这个小编译程序就能把一个大一点的编译程序译成机器语言------依此办理就能翻译一个更大的编译程序,直到最后得出整个所期望的编译程序。这个过程有个形象生动的名字:“自举”------其缘由是显然的(想象一个抓住鞋带想把自己举起来的人就行了)。这有点像一个刚刚能顺利地使用自己母语的幼儿,从那时开始,他的词汇量和流畅程度将飞速增长,因为他可以利用语言来取得新的语言。

运行着的程序的各种描述层次

编译语言一般说来并不反映运行由它所写出的程序的机器结构。这是它优于高度专门化的汇编语言和机器语言的主要特点之一。当然,在一个用编译语言书写的程序被翻译成机器语言之后,得到什么样的程序是依赖于具体机器的。因此,在描述一个正在执行的程序时,既可以独立于机器,也可以依赖于机器。正好像提到一本书中的某段时,既可以根据其谈论的内容(独立于出版社),也可以根据其页码(依赖于出版社)。

程序正常运行时,你怎么描述它或想象它的活动都没有太大关系。只有在出了毛病时,能够在不同的层次上思考才变得重要起来。例如,如果程序在某时要执行除法指令,而除数是零,程序将暂停运行,并把问题通知使用者,报告程序中出错的位置。但是,给出说明的层次往往低于程序员书写该程序的层次。下面是对一个嘎然而止的程序的三个平行的描述:

  • 机器语言层:“程序执行停止于1110010101110111位置”;

  • 汇编语言层:“程序执行停止于遇到DIV(除)指令时”;

  • 编译语言层:“程序执行停止于为代数表达式’(A+B)/Z’赋值的过程中”。

对于系统程序员(指那些编写编译程序、解释程序、汇编程序和其它一些供大家使用的程序的人)来说,最大的问题之一就是想办法编写查错子程序,以便给那些程序出错的用户提供高层而非低层的问题描述信息。一个有趣的颠倒是,如果一个遗传”程序”出毛病,(即出现一个突变),这时”错误”只能在高层次上显示给人们------即出现于表现型层次,而非遗传型层次。实际上,现代生物学把突变作为了解遗传过程的主要窗口之一,原因就是对这些过程可以在多个层次上进行探索。

微程序设计和操作系统

对于现代计算机系统来说,在层次结构中还有一些其它层次。例如,在有些系统中------通常是所谓”微型计算机”------其机器语言指令甚至比”把存储器中的一个数加到寄存器中的一个数上”那样的指令还要基本。使用者可以根据自己的意愿,决定需要哪些常规机器层次的指令来编程序,并且用机器提供的那些”微指令”来为所需的指令编制”微程序”。然后他所设计的这些”高级机器语言”的指令可以被做进电路中,从而成为硬件的一部分。当然不一定非要这样做。这种微程序设计使用户在一定程度上深入到通常的机器语言层之下。其结果之一就是一个厂家的一台计算机可以被”硬性联接”(通过微程序设计)成和同一个厂家------甚至另一个厂家------的另一台计算机具有相同的机器语言指令集。这个微程序化的计算机被称为在对另一台计算机进行”仿真”。

另一个层次是”操作系统”,它处于用机器语言写的程序和使用者进行程序设计的高级层次之间。操作系统本身是个程序,其功能是防止用户直接使用”裸机”(这就为系统提供了保护),并且使程序员摆脱许多非常琐碎繁杂的问题,如读入程序、调用翻译程序、运行翻译后的程序、把输出在适当的时候引向适当的通道、把控制权转交给下一个用户等等。如果多个用户同时与一个CPU”交谈”,那么操作系统将负责以某种有秩序的方式把系统的注意力从一个用户转向另一个用户。操作系统实在太复杂了,我只想通过下面的类比给一些提示。

请想想第一个电话系统。亚历山大·格雷厄姆·贝尔可以和另一间屋里的助手通电话。声音的电子传输就相当于一台没有操作系统的裸机:用电子计算!再看一个现代电话系统。你可以选择和哪一台电话接通。不仅如此,系统还可以同时控制多个不同的电话呼叫。你可以直拨、通过接线员接通、召开电话会议。你可能听到占线的嘟嘟声,也可能听到一个信号,警告你通话时间过长。你可以安装一台交换机,把附近的一批电话都联起来,如此等等。上面这个单子很惊人,你可以想想这是多么灵活,特别是和以前被当作奇迹的”裸”电话相比。现在复杂的操作系统就是为用户及其程序完成类似的通讯管理和层次转换操作的。实际上,在大脑中一定也发生着某种类似的事件:同时控制多种刺激;决定哪一种优先于其它种,优先权保持多久;紧急情况和偶发事件造成的突然”中断”,如此等等。

方便用户并保护系统

一个复杂的计算机系统中的许多层次,具有一种为用户提供”缓冲”的综合效用,使他可以不考虑许多低层活动。这些活动往往与他毫不相干。一个飞机乘客通常不想了解油箱里还有多少燃料、风速是多少、需要准备多少份饭、目的地附近的空中交通情况如何------这些事情已被交给航空公司系统中处于不同层次的工作人员来处理,而乘客只要求从一处到达另一处。同样,只有当出了什么毛病------比如他的行李没到,乘客才会意识到他以前不知道的那个使人迷乱的层次系统。

计算机是过于灵活还是过于刻板?

让人能尽可能自然地和计算机进行通讯,这一直是促使人们提高层次的主要目标之一。当然,和用机器语言写成的低层结构相比,用编译语言写成的高层结构更接近于人一般思考时所用的概念。但是,在这种使通讯更加容易的努力过程中,“自然”这个要求的一个方面被完全漠视了。事实上人际通讯中的约束远不像在人机通讯中那样刻板。例如,在寻找最好的表达方式时,我们常常说出无意义的句子片段:我们可能在说一句话的中间咳嗽;我们彼此打断对方的话;我们使用模棱两可的描述和”不规范”的句型;我们杜撰词组、歪曲意义------但我们的大部分信息一般仍能传递过去。用程序设计语言,一般说来是有着非常严格的句法的,你必须每时每刻遵守,而且没有模棱两可的词或结构。有趣的是,程序设计语言中也允许有对应于咳嗽的成分(即非本质性的或关系不大的注解),但要求它们必须以一个关键字作为开始信号(如COMMENT,即”注解”),然后终止于另一个关键字(如一个分号)。带有讽刺意味的是,即使是向灵活性作出的这样一个微弱姿态,也带有它自己的小陷阱:如果一个分号(或无论哪种表示注解结束的关键字)在一个注解内部被使用,翻译程序就会把这个分号理解成注解结束的标志,接着就是一场灾难。

假设程序中定义了一个叫”INSIGHT”(洞察)的过程,然后调用了它十七次,但第十八次由于程序员的大意,它被写成了”INSIHGT”。编译程序将徘徊不前,并刻板地打印出一个冷酷无情的错误通知,说它从来没听说过什么”INSIHGT”。编译程序发现了这样一个错误之后,它通常试图继续工作下去,但由于它没有洞察力,因此并没有理解程序员想要干什么。事实上,它可能会把这个错写的词设想成完全不同的东西,并且在那个错误的假设下工作下去。这时,一长串错误信息将雨点似地撒向程序的其余部分,因为编译程序------而非程序员------已经完全被弄糊涂了。可以想象,如果一个同声翻译正在把汉语译成俄语,突然在汉语中听到一个英语句子,然后就把后面的汉语都当成英语来翻译,这会造成多大的混乱。编译程序常常这样可怜地迷失方向。Thats life.

或许这听上去像是在谴责计算机,但实际上没有这个意思。从某种意义上说,这种情况是不可避免的。一旦你停下来想一下大多数人用计算机做什么,你将发现是要完成一些非常确定并精密的工作,这些工作太复杂,不适合由人来完成。如果计算机想要成为可靠的,那么它应当不带一点模棱两可地理解人希望它做的是什么。而且它必须既不多也不少地按照明确指示给它的去做。如果在为程序员提供方便的过程中,有一个程序的目的就是”猜测”程序员想做的事情,那么,下述情况是完全可以想象的:程序员设法传达了任务,但机器完全误解了。因此重要的是,对高层次的程序来说,在要求人用着合适的同时,仍应要求精确,没有歧义。

猜出程序员的意图

现在有可能设计一种容许某种不精确性的程序设计语言,以及一个能把它翻译到低层次上的翻译程序。一种可能的办法是让为这种程序设计语言服务的翻译程序设法弄懂那些”在语言的规则之外”所作的事情。但如果一种语言允许某些”犯规”,那么这种犯规已不再是真的犯规,因为它们已经被包容于规则之内了!如果一个程序员知道他可以出现某些种笔误,那么,他就会有意地利用语言这种特点,因为他知道他实际上是在刻板的语言规则范围内工作,尽管表面上看不是这样。换句话说,如果用户了解翻译程序为了他的方便而设置的所有灵活性,那么他也就知道了哪些界限是他所不能逾越的,因此在他看来,翻译程序仍然是刻板、不灵活的,虽然它和该语言的早期版本------它们没有体现”自动补偿人的错误”------相比是使人有了更多的自由。

对于那种”有弹性”的语言,可能出现的情况大概有两种:(1)用户了解构造在语言及其解释程序中的灵活性;(2)用户不了解这些灵活性。在前一种情况下,用户仍然可以用这种语言来精确地表达他的程序,因为他能预测计算机将怎样解释他用这种语言写的程序。在后一种情况下,解释过程具有一些隐蔽的特性,使得某些事件成为不可预测的(从不知道翻译程序内部工作方式的用户的角度看)。这可能导致对程序作出完全错误的解释,因此,在主要是出于速度和可行性的考虑而使用计算机的环境中,这样的语言是不合适的。

现在事实上还有第三种可能:(3)用户了解构造在语言及其翻译程序内部的各种灵活性,但由于它们为数众多,并以一种十分复杂的方式相互作用,致使用户无法断定他的程序会被怎样解释。这可能完全适用于翻译程序的设计者。他当然比别人更了解其内部情况------但他仍可能无法预测它对一个给定类型的不常见的结构将作出怎样的反应。

目前,在人工智能的研究中,主要的领域之一就是”自动程序设计”。这涉及到更高层次语言的开发------这些语言的翻译程序极其复杂,它们能做一些非常不容易的工作,例如:对例子进行概括、纠正某些笔误或语法错误、设法弄懂有歧义的描述的意思、利用一个基本用户模型来猜出用户的意图、对不清楚的事情进行提问、直接使用自然语言等等。我们希望在可靠性和灵活性之间走钢丝。

人工智能的进展即语言的进展

在计算机科学(特别是人工智能)的进展和新语言的开发之间有着非常紧密的相互联系。在过去的十年中出现了一个明显的趋势,即把新发现吸收到新语言之中。理解和构造智能的关键之一就存在于语言的不断开发和改进之中,用这些语言可以描述符号的处理过程。时至今日,已经有大约三四十种专门为人工智能研究所用的试验性语言被开发出来了。需要强调的是,应当认识到:任何可以用上述语言之一书写的程序,在原则上也能用更低层的语言来编制,但那需要人付出较大的努力,而且编出来的程序可能长得使人无法把握。每个较高的层次都没有扩展计算机的潜能,计算机的全部潜能已经存在于其机器语言指令集之中了。高层次语言中的新概念只不过是用它们的性质提示了一些方向和前景。

所有可能的程序所组成的”空间”是如此巨大,以致于没人能知道哪些东西是可能的。每种高层次语言都自然地适用于探索”程序空间”的某些特定区域,因此程序员在使用那种语言时,就被引入了程序空间的那些区域。语言并没有强迫他编写某类特定的程序,但语言为他做某些事情提供了便利。接近一个概念,一次轻微的推动,这些常常都是一个重大发现所需要的------而且这也是促使更高层的语言出现的动力。

使用不同的语言编程序就像使用不同的调式作曲,尤其是如果你是在钢琴键盘上作曲,那就更像了。如果你学过或写过不同调式的曲子,你会发现每个调式都有自己独特的感情色彩。同样,某种指法组合的使用方式对一个调式来说很自然,但对另一个调式可能就很别扭。因此,你所选择的调式对你就具有引导作用。甚至像升C和降D这样的等音调式都会以某种方式给人以不同的感受。这显示了一个记号系统会对最终产品产生相当大的影响。

图59.智能是个层次结构

为了构造智能程序,需要建造一个硬件和软件的层次结构,以解除在最低层观察一切所带来的痛苦。对同一个过程,不同层次的描述会是很不一样的,只有顶层是充分地组块化了,因此容易被人所理解。[摘自帕·亨·温斯顿,《人工智能》]

图59显示了一幅人工智能的”分层”图景,以机器元件(如晶体管)为底,以”智能程序”为顶。该图摘自帕特里克·亨利·温斯顿所著的《人工智能》一书,它代表了几乎为所有人工智能工作者所共有的关于人工智能的构想。虽然我同意人工智能应当以某种方式分层,但我并不认为通过这样少的几层就能达到智能程序。在机器语言层和真正达到智能的层次之间,我认为可能还需有十几层(甚至几十层)。每一个新的层次都基于下面一层,同时也扩展了下一层提供的灵活性。它们将是什么样的,我们现在做梦也想不出…

妄想狂和操作系统

计算机系统中各层次间的相似性会使人经历一种奇特的层次混淆。我有一次在观看两个朋友------都是计算机方面的新手------在一个终端上玩”帕里”程序。“帕里”是个名声不好的程序,它以一种极初等的方式模拟一个妄想症患者。它能用英语吐出一些陈词滥调,其中的词汇是从程序里的一个大词汇库中选出来的。它的行为挺逼真,因为它能够判断库存的词语中,哪些在用来回答人输入的英文句子时听起来更合理。

有一次,机器的反应时间很长------“帕里”要过很久才给答复------我向朋友们解释说,这可能是由于分时系统负担太重了。我告诉他们,只要打入一个特殊的”控制”字符,就可以进入操作系统,查出有多少用户在使用机器,而这在运行”帕里”时是看不到的。我的一个朋友按下了这个控制字符,转眼之间,某些关于操作系统状态的内部数据把”帕里”在屏幕上显示的一些词冲掉了。“帕里”对此一无所知:它的”知识”仅仅限于赛马和赌博------不是关于操作系统、终端和特殊控制字符的。但对我的朋友们来说,“帕里”和操作系统都不过是”计算机”------一个神秘、遥远、难以名状的实体,它可以对他们输入的信息作出回答。因此就完全可以理解为什么我那朋友这个时候会冒失地用自然语言打入下列问题:“为什么你把屏幕上的东西冲掉了?“我的朋友们不清楚”帕里”对于它下面的操作系统一无所知。“你”知道关于”你自己”的一切,这种想法在处理人际关系时为大家所熟知,因此很自然地会推广到计算机上------它毕竟还是具有足够智能的,它都能和他们用自然语言”交谈”!他们那个问题就像是问一个人:“你今天为什么制造了这样少的红血球?“人们不了解他们身体的那个层次------所谓”操作系统层次”。

这种层次混淆的主要原因是,人和计算机系统的所有层次之间的通讯都是在同一个终端的同一个屏幕上进行的。虽然说我的朋友似乎有点过于天真了,但若是一个复杂系统的几个层次同时出现在一个屏幕上,即使是有经验的计算机工作者也常常会犯类似的错误。他们忘了是在和”谁”谈话,于是输入了某些在那个层次上毫无意义的命令。因此,似乎应当要求系统本身能对层次进行区分------依据命令在哪一层能”有意义”来对它进行解释。不幸的是,这种解释要求系统具有大量的常识,还要有关于程序员的总体意图的完备知识------这两者都需要更多的人工智能,而这是目前还不具有的。

软件和硬件之间的界限

人们还常常会被某些层次上的灵活性和另一些层次上的刻板性给搞糊涂。例如,有些计算机具有很好的文本编辑系统,可以允许文本片段从一种格式中”倾注”到另一种格式中,就像液体可以从一个容器中被倾注到另一个容器中一样。窄页可以变成宽页,反过来也可以。它们既然有这么大的本事,人们就会期望从一种字体变成另一种------如从宋体变成楷体------也该是同样的容易。当然如果屏幕上只能显示一种字体,那这种转换就不可能了。也可能这种转换对屏幕是可行的,但在打印机上无法打印------还可能出现相反的情况。和计算机打交道久了,人常常被宠坏了,总觉得什么事情都能编程序解决:打印机不该刻板得只有一种或有限的几种字符集------字形应当是可以由用户指定的!但是一旦达到了这种灵活性,人们又会因打印机不能使用多种颜色的墨水而烦恼,或指责它不能接受任何形状和大小的纸张,或抱怨它不能在被打碎后再把自己装起来…

麻烦的事情在于,用第五章的话来说,所有这些灵活性都必须有个”终了”。在所有灵活性的下面必须是一个硬件层,而它是没有灵活性的。它可以藏得很深,上面的各个层次又提供了大量的灵活性,以致于没有多少用户能感到硬件的限制------但这种限制的存在是不可避免的。

软件和硬件间有区别,这是公认的,但到底是什么呢?就是程序和机器之间的区别------即长长的复杂的指令序列和执行它们的物理机器之间的区别。我喜欢把软件想象成”你可以通过电话线传送的任何东西”。一架钢琴是硬件,而乐谱是软件。一部电话机是硬件,而电话号码是软件。这种区分是很有用的,但也不是总能分得这样清楚。

我们人类同样有”软件”和”硬件”两个方面,它们的差别对我们来说是根深蒂固的。我们已经习惯于自己生理上的刻板性:我们事实上不能凭愿望治愈自己的疾病,或者长出任何颜色的头发------只举这两个简单的例子就够了。但是,我们能够为我们的心智”重新编程序”,这样我们就可以在一个新的概念框架中行动了。我们心智的惊人的灵活性似乎和下述观念水火不相容:我们的大脑一定是由具有固定规则的硬件构成的,不能被重新编程序。我们无法使我们的神经元兴奋得再快些或再慢些,我们无法重建它们之间的联系,我们无法重新设计一个神经元的内部结构,我们无法对硬件进行任何选择------但是,我们仍能控制自己的思维方式。

不过,显然我们的思维的某些方面是在我们的控制范围之外的。我们无法单凭愿望使自己聪明起来;我们无法以自己想要达到的速度去学会一门新的语言;我们无法使自己的思维速度比实际情况更快一些;我们无法使自己同时思考好几件事情;如此等等。这些基本的自我认识往往是不言而喻的,就像我们意识到周围有空气存在一样。我们从不真的费神去考察导致我们心智的这些”缺陷”的东西是什么:那就是我们的大脑组织。设想一些途径来调和心智的软件和大脑的硬件,这就是本书的一个主要目的。

中间层次和天气

我们已经看到,在计算机系统中有一些定义得很严格的层次,在每个层次上都能对一个正在运行的程序的操作进行描述。因此,不存在单一的低层次和单一的高层次------而是各种程度的低层次和高层次。中间层次的存在是否就是那些具有高低层次之分的系统的一般特征?一个例子,可以考虑这样一个系统:其”硬件”是地球的大气层(不是很硬,不过没关系),而其”软件”是天气情况。同时追寻所有分子的运动大概是一种对天气的非常低层次的”理解”方式,这很像在机器语言层观察一个巨大而又复杂的程序。显然这是超出人的理解能力的。但我们仍能用一些人类特有的方式来观察和描述天气现象。我们关于天气的组块化观点是基于层次很高的现象的,如雨、雾、雪、飓风、冷锋、季节、气压、信风、急流、积雨云、雷暴、逆温层等等。所有这些现象中涉及到的分子数量都达到了天文数字,它们以某种方式协同动作,造成了大尺度的天气趋势。这有点像读用高级语言描述的天气。

是否有某种东西类似于用中间层次语言来观察天气,比如像汇编语言那样?例如,是否存在非常小的局部范围内的”小型风暴”,就像人们偶尔见到的那种能搅起一股至多一米来宽尘土的小旋风那样?一个局部地区的阵风是否就是一种中间层次的组块,在一个高层天气现象的形成过程中发挥了作用?还是说我们没有切实可行的方法把关于这种现象的知识结合起来,以构造一个对天气的更容易理解的解释?

又有两个问题出现在我的脑海里。第一个问题:“是不是我们在自己的尺度上感知到的天气现象------一股龙卷风、一场旱灾等------只不过是中间层次的现象,是某种巨大、缓慢的现象的一部分?“如果是这样,那么真正的高层次天气现象应当是全球性的,而且采用地质学的时间尺度。冰河时代应当算是一个高层次天气事件。第二个问题:“是不是有这样的中层次天气现象:它们尚未被人所感知,但是一旦人们感知到它们,就会对天气的现状产生更深入的理解?”

从龙卷风到夸克

上面最后一种设想听起来有点离奇,但绝非不着边际。我们只须考察一下”硬科学”当中最硬的一个------物理学------就能发现这样的一些特殊系统,它们可以用相互作用的”成分”来解释,而这些成分本身却是不可见的。在物理学中,正像其它任何学科一样,一个”系统”是一组相互作用的”成分”。在我们了解的大多数系统中,这些成分在相互作用中保持着自身的特性,因此我们仍能在系统内部观察到这些成分。例如,当一队橄榄球运动员聚在一起的时候,每个运动员都保持着自身的独立性------他们并没有融化进某个复合实体,从而消失了自己的独立性。但是------这是很重要的------在他们的大脑中进行着某些过程。这些过程是被球队这种环境所诱发的,否则它们不会发生。因此,在某种微弱的程度上可以说,这些队员在成为一个更大的系统(即球队)的一部分时,他们自身的个性已经有所改变。这种系统被称为”几乎可分解系统”(这个名称来自赫·西蒙的文章《复杂性的结构》)。这样的系统包含相互作用较弱的模块,每个模块在相互作用过程中保持自己独有的个性,但变得有些不同于它在系统之外时的状况,以此保证了系统的聚合性行为。物理学所研究的系统通常都是这种类型的。例如,可以认为原子中包含一个原子核,它所带的正电荷把若干电子俘获到”轨道”上,或者说使它们处于约束状态。被约束的电子很像自由电子,尽管它们处在一个复合对象的内部。

物理学中所研究的另一些系统和比较简单明确的原子恰成一鲜明对照。这些系统中包含着极强的相互作用,结果是其成分都被系统所吞没,丧失了它们的部分或全部个性。其中一个例子就是原子核。原子核通常被描述成”由质子和中子所组成”。但把作为其成分的粒子拉到一起的力实在太强了,因此这些粒子的存在方式完全不同于其”自由”形态(即它们在原子核外时所处的形态),而且事实上一个原子核的活动在很多方面都像单个的粒子,而不像一组相互作用的粒子。当一个原子核分裂时,常常释放出质子和中子,但也会释放出其它粒子,如π介子和γ射线都是通常会产生的。是所有这些不同的粒子在原子核分裂前就都实实在在地存在于其中,还是说它们只不过是原子核分裂时迸溅出的”火花”?或许回答这样一个问题的尝试本身就是没有意义的。在核子物理学的层次上,是存储了产生”火花”的潜力,还是存储了实在的粒子,这两者的差别不是很明显的。

因此,原子核就是这样一个系统:它的成分虽然在其内部是不可见的,但可以被拉出来变为可见的。但是,还有一些更反常的情况,例如把质子和中子看成系统就会如此。质子和中子都被设想成是由三个”夸克”构成的,而夸克是一种假想的粒子,它们可以三三两两结合成许多已知的基本粒子。但是,夸克间的相互作用实在太强了,致使它们不仅不能在质子和中子内部被观察到,而且甚至根本就拉不出来!这样,虽然夸克在理论上有助于理解质子和中子的某些性质,它们自身的存在可能永远不会被单独地确认。在这里我们得到了”几乎可分解”系统的反义词------这种系统是”几乎不可分解”的。但不可思议的是,关于质子和中子(以及其它粒子)的一个基于夸克的理论具有可观的解释力。使用”夸克模型”,可以很好地定量说明许多涉及到假设由夸克构成的粒子的实验结果。

超导:一个关于重正化的”悖论”

在第五章中,我们已经讨论过被重正的粒子从它们的裸核中产生的过程,即通过虚粒子递归复合地相互作用。一个被重正的粒子既可以被看成是这个复杂的数学建构,也可以看成单一的实在团块。对粒子的这种描述方式所导致的最奇特也最有戏剧性的结果之一,就是为著名的”超导”现象所提供的解释。超导就是指在极低的温度下,电子可以在某些固体中无阻抗地流动。

据发现,固体中的电子是由它们自己与一些称为”声子”的奇特的振动量子之间的相互作用所重正的(声子自己也被重正了!)。这些重正后的电子称为”极化子”。计算表明,在极低的温度下,两个自旋相反的极化子将开始互相吸引,而且确实能以某种确定的方式约束在一起。在适当的条件下,所有载流极化子将两两结合,形成”库珀对”。具有讽刺意味的是,这种结合的产生完全是由于电子------成对的极化子的裸核------相互之间的电斥力。与电子相反,库珀对之间既不相吸也不相斥,结果一个库珀对可以自由地通过一块金属,就像这块金属是真空一样。如果你把对这样一块金属的数学描述从以极化子为基本单位转换成以库珀对为基本单位,你就能得到一组明显地简化了的方程式。这种数学简单性就是物理学家的认识方式,他们知道形成库珀对这样的”组块”对观察超导来说是一种很自然的方式。

这里我们就有若干个层次的粒子:库珀对自身、构成它的两个自旋方向相反的极化子、构成极化子的电子和声子,然后,在电子内部,还有虚拟的光子和正电子,如此等等。我们可以观察某个层次,看到在那里出现的现象,而这些现象可以通过对下面几个层次的理解而得到解释。

“隔  离”

类似地,同时也是幸运地,人们不必了解关于夸克的全部情况,仍能对那些大概是由它们构成的粒子进行深入的理解。这样,一个核物理学家可以使用基于质子和中子的理论,而不必考虑夸克理论及其竞争对手。核物理学家有一幅关于质子和中子的组块化图像------一个从低层理论中推导出的描述,但这并不需要了解低层理论。同样,一个原子物理学家有一幅从原子核理论中推导出的关于原子核的组块化图像。然后一个化学家有一幅关于电子及其轨道的组块化图像,并且构造了关于小分子的理论。这一理论可以以组块化的形式被分子生物学家所接收,他们有关于小分子如何挂在一起的直觉,但其技术专长是在超大分子及其相互作用的领域之中。然后细胞生物学家又有一幅组块化的图像,其中的基本单位是分子生物学家所思考的,而细胞生物学家只是设法用这些基本单位说明细胞相互作用的方式。问题很清楚。每个层次都是在某种意义下被”隔离”于下面的层次的。这个生动的说法也是西蒙所提供的,这使我们想起潜水艇建造水密舱的方式:如果一个部分损坏了,水会涌进来,但只要关闭舱门,损坏的舱室就被隔离开了,这样可以防止乱子的蔓延。

在科学的层次结构中,层次间总是有些”渗漏”的,因此化学家无法完全不考虑低层的物理学,生物学家也无法完全不考虑化学,但是,两个相距较远的层次间几乎是没有渗漏的。这就解释了为什么人们可以直觉地理解别人,而无须懂得夸克模型、原子核结构、电子轨道的性质、化学键、蛋白质构造、细胞中的细胞器、细胞间的通讯方式、人体各种器官的生理学、或器官间复杂的相互作用。一个人所需的一切不过是一个关于最高层活动方式的模型。众所周知,这样的模型是非常实际也非常有效的。

组块化和确定性之间的利弊权衡

然而,组块化模型可能有个很大的缺点:它通常不具有精确的预测力。这就是说,通过使用组块化模型,我们不必力不从心地把人看作夸克(或某种更低层的东西)的集合,但显然这种模型只能让我们或然地估计别人的感觉、别人对我们的言行的反应,如此等等。简而言之,在使用组块化的高层模型时,我们为简单性牺牲了确定性。尽管我们不能确定人们将会对一个笑话作何反应,我们说这个笑话时仍预期着他们的某些行为,诸如笑或者不笑------而不是,比如说,爬到最近的一根旗杆上去。(但禅宗大师可能会这样干!)一个组块化模型是:定义一个”空间”,并预期着行为会落入其中,而且描述了行为落在该空间的不同区域的概率。

“计算机只能做你告诉它去做的事”

上述想法既能用于复合的物理系统,也能用于计算机程序。有一种老生常谈的说法,即”计算机只能做你告诉它去做的事。“这在某种意义下是对的,但并没有说到点子上:你不能预先知道你告诉计算机去做的事会导致什么结果,因此它的行为可能像一个人那样令人迷惑、使人惊讶、无法预测。你一般事先知道它的输出会落在哪个空间里,但你不知道其细节。例如,你可以写一个程序来计算π的前一百万位。你的计算机会以比你快得多的速度打出前四十位------计算机超过了它的程序员,但这不会导致悖论。你事先知道输出会出现在哪个空间------即0到9之间的数字空间------这就是说,你有一个关于程序行为的组块化模型,但假设你连剩下的也都知道了,那你也就不会去写这个程序了。

说这句老话过时了,还有另外一层意思。它涉及到这样一个事实:你编程序的语言层次越高,你越无法精确地知道你让计算机所干的事!一层一层的翻译把一个复杂程序的”用户界面”和实际的机器指令分隔开了。在你思考和编程序的层次上,你的语句可能更类似于陈述句和建议,而不太类似于祈使句和命令。一般说来,一个高层语句的输入所诱发的内部过程对你来说是不可见的,正好像在吃饭的时候,你用不着明确意识到由此触发的消化过程。

“计算机只能做人告诉它去做的事”,这是由洛芙莱丝命妇在她有名的回忆录中首先提出的。这个观点一直很流行,而且往往联系于另一个观点:“计算机不能思维”。关于后者,我们将在后面的章节中再来讨论,那时我们会更老练些。

两类系统

在下述两类由许多部分构成的系统之间存在着一种重要的区别。在一类系统中,某些部分的行为趋向于抵消另一些部分的行为,结果是低层发生的事件影响不大,因为大多数事件都将导致类似的高层行为。这种系统的一个例子就是煤气罐,它里面的分子以非常复杂的微观方式彼此碰撞,但总的效果,在宏观上看,它是一个非常平静、稳定的系统,具有一定的温度、压力和容量。而在另一类系统中,单个低层事件的效果将被放大成一个巨大的高层后果。克郎棋就是这样的一个系统,其中棋子间的碰撞对整个局势的变化会产生重要的影响。

计算机是这两类系统的一个复杂的结合。它有像导线这样的构件,其行为方式是可以准确预测的,其导电过程服从欧姆定律这样一个非常精确的组块化定律,这类似于煤气罐里的煤气所服从的定律。因为导线的行为取决于统计效应,其中成千上万的随机事件彼此抵消,导致了整体行为的可预测性。计算机中也有像打印机这样的宏观构件,它们的行为完全决定于电流的精确模式。打印机的打印结果可不是被大量相互抵消的微观效应造成的。事实上,对大多数计算机程序来说,程序中每一位的值都对打印的结果起着关键性的作用。如果任何一位被改变,输出也会大幅度地改变。

那些仅仅由”可靠的”子系统组成的系统------即其子系统的行为都可以从组块化的描述中可靠地被预测出来------在我们的日常生活中发挥着无法估量的重要作用,因为它是稳定性的柱石。我们可以相信墙不会倒、人行道今天和昨天通向同一个地方、太阳会发光、钟表会指示正确的时间,如此等等。这种系统的组块化模型实际上是完全确定的。当然,另一类系统在我们的生活中也起了很大作用,它们的行为是可变的,取决于某些我们无法直接观测的微观参数------而且这些参数往往为数众多。对这样的系统来说,我们的组块化模型必须以操作空间的形式出现,并且能对结果落入空间的不同区域的可能性给出概率估计。

正像我已经指出的那样,煤气罐是一个可靠系统,其原因是许多相互抵消的效应最终遵从精确的、确定性的物理定律。这种定律是组块化的,它们把罐里的煤气看作一个整体,不管它的组成部分。而且,对煤气的微观和宏观描述使用的是完全不同的词汇。前者需要说明其中每一个分子的位置和速度,而后者只需要说明三个新引进的量:温度、压力和容量,并且前两个量甚至根本没有微观对应物。把这三个参数联系在一起的简单数学关系------pV=cT,其中c是个常数------是一条既依赖于低层现象,又独立于低层现象的定律。说得再明白一点,这条定律可以从主宰着分子层次的定律中被推导出来,在这个意义上它依赖于低层。另一方面,这条定律允许你完全不考虑低层,如果你愿意的话。在这个意义上它又独立于低层。

重要的是,要认识到高层定律是不能用低层描述的词汇表里的词来叙述的。“压力”和”温度”是一些新词,它们所代表的经验是不能在低层次上传达的。我们人是直接感知温度和压力的,我们的构造就是如此,因此我们能发现这一定律也就不足为奇了。但如果有一种生物仅把气体看作纯理论的数学结构,那它们在发现这一定律时就必须具有一种综合出新概念的能力。

旁效现象

在本章快要结束的时候,我想讲一段与一个复杂系统有关的往事。一天,我在和两个系统程序员谈论我所用的计算机。他们说操作系统在应付三十五个以内的用户时并不感到困难,但在达到三十五个用户左右时,反应时间突然一下子长了起来,慢得好像你都可以退出系统回家去等着。我开玩笑说:“这好办------看看操作系统里哪个地方存着’35’这个数,然后把它改成’60’不就行了!”大家都笑了。当然,问题在于根本没有这种地方。那么这个临界值------35个用户------是从哪里来的呢?答案是:它是整个系统组织的一个可以看见的结果------一个”旁效现象”。

类似地,你可以去问一个短跑运动员:“你能用10秒5跑100米,那10秒5这个数字存储在你身体里的什么地方?“显然,哪里也没有。这个时间是他的身体构造和他的反应时间的一个结果。在他跑的时候,有成千上万个因素在相互作用。这个时间是完全可以再现的,但它却没有存储在他体内的任何地方。它分布在他身体的所有细胞中,只有在奔跑的行动中才能表现出来。

旁效现象随处可见。我们都知道在围棋里,“两个眼可以活”。这不是写在规则中的,但这又是运用规则的结果。对人脑来说,“上当受骗”就是这样一种性质。你容易上当吗?是不是你脑子里有个”上当中心”?如果是这样的,能不能找个神经外科医生,打开你的头骨做一个精巧的手术,以后你就会少上当了?如果你相信这种观点,那你可就太容易上当了,或许你应当考虑去做这样一个手术。

心智之别于大脑

在后面几章中,我们将讨论大脑,检验一下是否可以理解大脑的顶层------心智------而不必先去理解那些它既依赖又不依赖的较低层次。是否存在这样一些思维定律:它们可以被”隔离”于那些控制着微观的脑细胞活动的低层定律?是否能把心智从大脑上”撇出来”------就像把油从汤的表面上撇出来那样------然后移植到其它系统中去?或许根本就不可能把思维过程分解到整齐的、模块化的子系统中去?大脑是更像一个原子,还是更像一个重正后的电子,或一个原子核、一个中子、一个夸克?自我意识是一种旁效现象吗?为了理解心智,我们是否一定要深入到神经细胞的层次?

Footnotes

  1. 制作者注:超级计算机”深蓝”在1997年5月击败了国际象棋世界冠军卡斯帕罗夫;浪潮天梭在2006年8月击败了由柳大华等五位中国象棋大师组成的大师队;而在围棋领域,计算机至今(2015年)仍与人类高手差距巨大。本书作者侯世达教授在深蓝战胜卡斯帕罗夫后评论说”这是历史性的转折,但和电脑变聪明了没有关系”(据维基百科”侯世达”)[个人观点:本质上这些棋手大师对抗的是一大群人(包括了棋手大师以及计算机领域的专家)合力设计出来的计算机程序,但是这些个程序除了下棋其实并不会做其他事情]。

  2. 制作者注:现代计算机字长一般为2的整数次方,即16位、32位、64位等。