or
    or - 图1
    这个表是:
    or - 图2
    或者
    or - 图3

    (最后一行末尾的句号是以“这个表是……”开头的句子的一部分。)这个表暗示 or - 图4 (or - 图5 x)是机器的另一个m-格局。从下面的推广可以看出,or - 图6 (or - 图7 x)同样也是机器的另一个m-格局。

    Or, in greater detail:
    or - 图8
    或者,更详细地表示为:
    or - 图9

    (同样,最后一行or - 图10之后的句号表示这个表被当成了句子的一部分。)注意,擦除字符后,or - 图11转向 or - 图12 已经是这台机器的一个m-格局了,因此,不会导致m-格局的无限产生。

    In this we could replace or - 图13 x) by or - 图14 and then give the table for or - 图15 (with the right substitutions) ad eventually reach a table in which no m-functions appeared.
    这里,我们使用 or - 图16 代替 or - 图17 x),然后给出or - 图18的表(进行适当地代换),最终可以得到一个不包含任何m-函数的表。

    正如图灵使用or - 图19来代表格局or - 图20(or - 图21, x)一样,他还可以使用or - 图22表示or - 图23,x), 使用其他的格局来表示or - 图24or - 图25

    现在,我们已经掌握了这些函数(才怪!),图灵不断地积累这些函数。我知道,现在我们很难看出这些函数是如何恰当地搭配在一起的。为了构造通用机,图灵需要一些操作单个字符或字符串的通用类型的函数。读者已经看到了查找和擦除函数。他还需要剪切、复制、粘贴和一些标准打印函数。

    函数or - 图26表示“在结尾打印”。它在第一个空的F-格处打印β表示的符号。

    or - 图27
    or - 图28

    这个函数隐藏着一些假设。通常情况下,or - 图29寻找其第三个参数在最左边的第一次出现,但是这里的or - 图30第三个参数是一个中央元音,它也是or - 图31为到达序列最左边所要寻找的符号。于是,正如图灵在第85页给出的第二个机器的例子,函数or - 图32也假设每行中存在两个中央元音。这个m-函数or - 图33首先找到这两个中央元音中最右边的一个(出现在E-格的那个),然后把读写头左移置于左边F-格的中央元音处。随后,函数or - 图34 沿着F-格向右移动,直到找到一个空格,并在此打印一个β字符,对于大多数计算机器来说,这个β将是0或1。

    接下来的例子都很有技巧。图灵首先定义了两个名字分别为 or - 图35(指左边的)和 or - 图36(指右边的)的函数,然后分别用它们与or - 图37结合得到另外两个函数or - 图38or - 图39。这两个新的函数在找到所需字符后会将读写头向左或者向右移动。

    or - 图40
    or - 图41

    我本应该把它们称为or - 图42or - 图43,而非or - 图44or - 图45,但那只是我的想法。

    通用机会要求把字符从纸带的一个位置移动到另一个位置上。函数or - 图46的功能是“复制”。字符α更可能是一个标记。or - 图47首先找到这个标记左边的F-格里的字符,然后使用or - 图48将该字符复制到尾部第一个空的F-格中。

    or - 图49
    or - 图50

    注意上面的函数使用or - 图51来寻找字符α,因此操作结束的时候读写头位于标记的左边,正好是这个标记指示的字符处。

    or - 图52函数的语法比较独特:扫描到的字符成为了or - 图53的第二个参数。图灵说:

    [238]
    The last line stands for the totality of lines obtainable from it by replacing β by any symbol which may occur on the tape of the machine concerned.
    最后一行代表了用机器纸带上可能出现的任意符号代替β后得到的所有的行。

    例如,如果函数or - 图54只用来复制0或1,那么事实上,or - 图55会被定义成:

    or - 图56

    函数or - 图57代表了“复制并擦除”。它也有分别包含两参数和三参数的版本。

    or - 图58
    or - 图59

    带三个参数的or - 图60首先使用or - 图61复制最左边被α标记的数字,然后使用or - 图62擦除这个标记。带两个参数的or - 图63则使用三参数版本的函数来复制第一个数字并擦除标记,然后再转向两参数版本的函数。实际上,所有标记为α的符号都被复制到纸带尾部第一批可用的F-格里。(在第77页图灵的第二个例子中,本可以使用这个函数把一连串的1复制到纸带的尾部。)

    是时候提出效率这个令人生畏的问题了。图灵定义的函数看上去很精密紧凑,但事实上里面隐藏着巨大的工作量。为了执行一次复制和擦除,函数or - 图64要使用or - 图65来寻找标记(并记住or - 图66要一路回溯到哨兵),然后再使用or - 图67,而or - 图68又要调用or - 图69来找到相同的标记后才能将其擦除。一种更高效的方法是使用or - 图70在第一次找到某个标记,并在复制字符之前就将其擦除。(为了纪念图灵机臭名昭著的低性能,我们使用“图灵沥青坑”[2]一词来描述过度一般化的计算机例程,准备这些例程比运行它们花费的时间更多。)

    但是,图灵并不关心效率问题,毕竟,机器都是想象出来的。如果他愿意,可以以106 ZHz[3]的频率来运行机器,没有人会考虑做了多少无用工。

    函数or - 图71是指“替换”。假设参数α和β都是标记。函数找到最左边的α,并用β替换它。(因为图灵不允许替换已经在F-格中标记的字符,因此我们可知α和β是标记。)

    or - 图72
    or - 图73

    三参数版本的函数用β替换所有的α标记。

    or - 图74
    or - 图75

    为了保持一致,右边的解释部分的第一行应该缩进两个字符。

    如果你已经熟悉了图灵的方法和命名规则,就会知道下面这个函数or - 图76是用来完成“复制和替换”的。

    or - 图77
    or - 图78

    图灵论文的其他地方没有使用到这些函数。

    通用机要求有“搜索并替换”功能,于是图灵接着用了半页的篇幅展示了or - 图79(“比较”)和 or - 图80(“比较并擦除”)函数。由于这些函数里的最终m-格局太长,因而图灵的解释没有放在每个表的右边,而是放在了下面。(第一行有个错误:最终m-格局列中or - 图81的下标1应该是逗号。在该列出现的一些句号也没有任何意义。)

    or - 图82
    The first symbol marked alpha; and the first marked β are compared. If there is neither α nor β, → or - 图83 If there are both and the symbols are alike, →or - 图84 Otherwise →or - 图85
    or - 图86
    or - 图87 differs from or - 图88 α, β) in that in the case when there is similarity the first α and β are erased.
    or - 图89
    or - 图90 α, β). The sequence of symbols marked α is compared with the sequence marked β → or - 图91 if they are similar. Otherwise → or - 图92 Some of the symbols α and β are erased.
    or - 图93
    比较第一个α标记的字符和第一个β标记的字符。如果即没有标记α也没有标记β,则→or - 图94。如果标记α和β都存在,并且所标记的字符一样,那么→or - 图95;否则→or - 图96
    or - 图97
    or - 图98or - 图99 α, β)的不同之处在于,如果存在一对相同的字符,那么第一个α和β将被擦除。
    or - 图100
    or - 图101 α, β),比较α标记的符号序列和β标记的符号序列。如果它们是相似的,则→or - 图102;否则→or - 图103。一些α和β将被擦除。

    图灵在这里所说的“相似”是指“完全相同”。

    现在,图灵已经用完了他能想到的容易记忆的所有函数名称,因为他把接下来的函数仅简单命名为or - 图104。不幸的是,这也是一般情况下他用来表示m-格局的字母;更糟糕的是,后文中他使用or - 图105来指代这个函数。

    我相信,图灵本意是想用or - 图106来命名这个函数,而不是用or - 图107。类似函数or - 图108用来寻找某个符号(最左边)的第一次出现,这个函数是用来寻找某个符号(最右边)的最后一次出现的。用两个连续的字母来表示有关联的两个or - 图109or - 图110函数是有意义的,因此,尽管接下来的表里描述的是函数or - 图111,我将使用or - 图112来指代该函数。

    只有一个参数的函数or - 图113将读写头右移,直到它在一行中找到两个空格。我们假设那里处于纸带的最右端。带两个参数的函数or - 图114首先使用只有一个参数的or - 图115,然后再向左移动寻找字符α。

    [239]
    or - 图116
    or - 图117

    在本节的最后,图灵给出了一些名字很熟悉的辅助函数。

    回想一下,函数or - 图118用来在最后一个F-格中打印一个字符。函数or - 图1192在最后两个F-格中打印两个字符。

    or - 图120
    or - 图121

    类似地,函数or - 图122用来将α标记的字符复制到尾部。函数or - 图1232则复制α和β标记的字符,函数or - 图1243复制α、β和γ标记的字符。

    or - 图125
    or - 图126

    这些复制是顺序执行的:首先复制所有α标记的字符,其次复制所有β标记的字符,以此类推。图灵使用了带6个参数的函数or - 图127,这个函数虽然之前没有描述过,但是它的操作是显而易见的。

    最后,只有一个参数的函数or - 图128擦除所有的标记。

    or - 图129
    or - 图130

    年长点的程序员可能知道一本由Pascal语言的创始人尼克劳斯·威茨(1934—)编著的书,书名非常美妙,叫作《算法+数据结构=程序》(Prentice-Hall,1975年出版)。顾名思义,一段计算机程序包括代码(算法)和代码处理的数据。至此,图灵已经展示了他的通用机所需的诸多算法,但是还没有描述如何让一台计算机器来成功地处理数据。这就是接下来要讲的内容。