# 《计算机程序的构造和解释》序言，1996 年和 1984 年

> 原文：[Prefaces to Structure and Interpretation of Computer Programs, 1996 & 1984](https://sourceacademy.org/sicpjs/1)
> 
> 译者：[飞龙](https://github.com/wizardforcel)
> 
> 协议：[CC BY-NC-SA 4.0](https://creativecommons.org/licenses/by-nc-sa/4.0/)

## 《SICP》第二版序言，1996 年

> 软件可能不像其他任何东西，它可能是用来丢弃的：整个重点是始终将其视为肥皂泡吗？
> 
> ——艾伦·J·佩里斯

自 1980 年以来，本书的内容一直是麻省理工学院入门级计算机科学课程的基础。在第一版出版时，我们已经教授了这些内容四年，直到第二版出现为止，又过去了十二年。我们很高兴看到我们的工作被广泛采用并融入其他教材中。我们看到我们的学生将本书中的思想和程序作为新计算机系统和语言的核心进行构建。在对古代犹太文学的双关语的实际实现中，我们的学生已经成为我们的建设者。我们很幸运有这样有能力的学生和有成就的建设者。

在准备这个版本时，我们吸收了数百个澄清建议，这些建议来自我们自己的教学经验以及麻省理工学院和其他地方的同事的评论。我们重新设计了书中大部分主要的编程系统，包括通用算术系统、解释器、寄存器机模拟器和编译器；我们重新编写了所有的程序示例，以确保符合 IEEE Scheme 标准（IEEE 1990）的任何 Scheme 实现都能运行这些代码。

这个版本强调了几个新主题。其中最重要的是不同时间处理方法在计算模型中所起的核心作用：具有状态的对象、并发编程、函数式编程、惰性求值和非确定性编程。我们增加了关于并发和非确定性的新章节，并试图贯穿整本书的主题。

该书的第一版紧随我们麻省理工学院一个学期的课程大纲。随着第二版中的所有新材料，不可能在一个学期内覆盖所有内容，因此教师将不得不进行选择。在我们自己的教学中，我们有时会跳过逻辑编程部分（第 4.4 节），我们让学生使用寄存器机模拟器，但我们不涉及其实现（第 5.2 节），我们只对编译器进行了简要概述（第 5.5 节）。即便如此，这仍然是一门密集的课程。一些教师可能只希望覆盖前三四章，将其他材料留给后续课程。

麻省理工学院出版社的网站为本书的用户提供支持。这包括书中的程序、示例编程作业、补充材料以及 Lisp 方言 Scheme 的可下载实现。

—哈罗德·阿贝尔森和杰拉尔德·杰伊·萨斯曼

## 《SICP》第一版序言，1984 年

> 计算机就像小提琴。你可以想象一个新手先尝试留声机，然后再尝试小提琴。他说后者听起来很糟糕。这就是我们从人文学家和大多数计算机科学家那里听到的论点。他们说，计算机程序对特定目的很好，但不够灵活。小提琴和打字机也是如此，直到你学会如何使用它们。
> 
> ——马文·明斯基，“为什么编程是表达不清楚和粗糙构想的好媒介”

《计算机程序的结构与解释》是麻省理工学院计算机科学的入门课程。对于主修电气工程或计算机科学的麻省理工学院学生来说，这是“通识核心课程”的一部分，该核心课程还包括两门有关电路和线性系统的课程以及一门关于数字系统设计的课程。自 1978 年以来，我们一直参与该课程的开发，并自 1980 年秋季起以目前的形式教授该课程，每年约有 600 至 700 名学生。大多数学生在计算方面几乎没有或根本没有正式的训练，尽管许多人稍微接触过计算机，有些人有丰富的编程或硬件设计经验。

我们设计这门计算机科学入门课程的两个主要关注点。首先，我们希望确立一个观念，即计算机语言不仅仅是让计算机执行操作的一种方式，而是一种表达方法论思想的新颖形式。因此，程序必须是为人们而写的，只是偶然为机器执行。其次，我们认为在这个层次上需要解决的基本问题不是特定编程语言结构的语法，也不是计算特定函数的巧妙算法，甚至不是算法的数学分析和计算基础，而是控制大型软件系统的知识复杂性的技术。

我们的目标是，完成这门课程的学生应该对编程的风格和美学元素有所了解。他们应该掌握大型系统中控制复杂性的主要技术。如果程序以示范的风格编写，他们应该能够阅读长达 50 页的程序。他们应该知道什么不需要阅读，以及在任何时候他们不需要理解什么。他们应该对修改程序感到自信，保留原作者的精神和风格。

这些技能并不是计算机编程所特有的。我们教授和借鉴的技术是所有工程设计的共同之处。我们通过构建隐藏细节的抽象来控制复杂性。我们通过建立常规接口来控制复杂性，这使我们能够以“混搭”的方式组合标准、理解透彻的部件来构建系统。我们通过建立描述设计的新语言来控制复杂性，每种语言都强调设计的特定方面并淡化其他方面。

我们对这门课程的方法的基础是我们的信念，即“计算机科学”并不是一门科学，它的重要性与计算机无关。计算机革命是我们思考方式和表达思想方式的革命。这种变化的本质是最好称为“程序式认识论”的出现——从命令的角度研究知识结构，而不是古典数学学科所采用的更为陈述性的观点。数学提供了处理“是什么”的概念的精确框架。计算提供了处理“如何”的概念的精确框架。

在教授我们的材料时，我们使用的是 Lisp 编程语言的一个方言。我们从不正式教授这种语言，因为我们不必这样做。我们只是使用它，学生们几天就能掌握。这是 Lisp 类语言的一个巨大优势：它们几乎没有形成复合表达式的方式，几乎没有语法结构。所有的形式属性都可以在一个小时内覆盖，就像国际象棋的规则一样。过了一段时间，我们就会忘记语言的语法细节（因为几乎没有），并着手处理真正的问题——弄清楚我们想要计算什么，如何将问题分解为可管理的部分，以及如何处理这些部分。Lisp 的另一个优势是，它支持（但不强制）更多的程序模块化分解的大规模策略，比我们所知道的任何其他语言都要多。我们可以进行过程和数据抽象，我们可以使用高阶函数来捕捉常见的使用模式，我们可以使用赋值和数据变异来模拟局部状态，我们可以使用流和延迟求值来链接程序的部分，我们可以轻松实现嵌入式语言。所有这些都嵌入在一个交互式环境中，具有出色的支持，用于增量程序设计、构建、测试和调试。我们感谢所有世代的 Lisp 巫师，从 John McCarthy 开始，他们打造了一种前所未有的强大而优雅的工具。

Scheme，我们使用的 Lisp 方言，是试图将 Lisp 和 Algol 的力量和优雅结合在一起的尝试。从 Lisp 中，我们获得了源自简单语法、将程序统一表示为数据对象以及垃圾回收堆分配数据的元语言能力。从 Algol 中，我们获得了词法作用域和块结构，这些都是编程语言设计先驱在 Algol 委员会上的贡献。我们希望引用 John Reynolds 和 Peter Landin 对 Church 的λ演算与编程语言结构关系的洞察。我们也承认我们对数学家的债务，他们在计算机出现之前就已经勘探了这个领域。这些先驱包括 Alonzo Church，Barkley Rosser，Stephen Kleene 和 Haskell Curry。

—Harold Abelson 和 Gerald Jay Sussman
