the little schemer 笔记
Z.X.L
2012年08月13日
五项规则
car的规则
car只对非空列表有定义。
cdr的规则
cdr只对非空列表有定义。任何非空列表的cdr是另外一个列表。
cons的规则
cons有两个参数。cons的第二个参数必须是一个list,结果也是一个list。
Null的规则
Null仅为list定义。
eq的规则
eq有两个参数。每一个参数都是非数值atom
The Little Schemer
Forth Edition
原作者
Daniel P. Friedman
Indianna University
Bloomington, Indiana
Matthias Felleisen
Rice University
Houston Texas
The MIT Press
Cambridge, Massachusetts
London, England
前言
此前言是第三版The Little LISPer 的前言。经过作者的允许,我们把它放在这里。
1976年,我在学习摄影入门。大多数学生(包括我)学习这们课程是为了变得跟有创造力——拍摄出我敬仰的艺术家Edward Weston那样的艺术作品。第一天,老师耐心的讲解了我们这学期将要学习到的技术技巧。重点是Ansel Adams的“Zone System”,用来预可视化冲印照片的值(打印的亮度)和在场景中获得他们的光照强度。为了获得这种技术,我们必须学会使用曝光计测量光的强度和曝光时间的使用和发展的时间来控制的黑色层次和图像的对比度。而这需要耕地层次的技术比如装底片,开发及冲印,混合化学品。摄影师必须学会仪式化敏感材料制定的过程中,使 多年的工作,得到一致的结果。第一次进实验室,满是滑湿的手感,定影液臭气熏天。
但是创意成分呢?为了有创造力,你必须要能控制媒介。没有这些必备的技能是不可能拍摄出伟大的摄影作品的。工程技术,其他的创造性的艺术,我们必须学习分析来支持综合的成果。一个人不可能没有钢铁泥土的知识和计算结构的数学技术去建造一座华丽和实用的桥梁。同样一个人不可能不深入理解如何“预可视化”他/她写的程序产生的进程而构造出精巧的的计算机系统。
一些摄影师选择8×10格而其他人选择35mm的片,这各有各的有缺点。如同摄影,编程序需要选择媒介。Lisp是一种*和富有弹性的媒介。Lisp是为递归论和符号代数而构造的理论体系。它已经发展成为一个独一无二的强大和灵活的软件开发工具的家庭体系,Lisp为快速原型软件系统提供wrap-around支持。与其他语言一起,Lisp为了使用用户社区提交的各种巨大的库当作胶水语言。Lisp中,procedures是一等数据,被当作参数,返回值,存储在数据中。这种弹性是有价值的,并且更重要的是它提供了通用模式使用必不可少的工程设计——idioms——的正式设立,命名和简化的机制。另外,Lisp程序可以很容易地操控Lisp程序。这是一个推动程序合成和分析工具大力发展的功能,例如交叉引用。The Little Lisper方法独特以培养读者在Lisp中基础的创意的编程技能。它循序渐进的包含了学习构造递归和操作递归数据结构所需要的训练和练习。The Little LISPer对与学生学习Lisp程序犹如Hanon的指法练习或者Czerny的练习曲对于学生学习钢琴弹奏一样。
Gerald J. Sussman
Gambridge, Massachusetts
Preface
为了庆祝Scheme的20周年纪念,我们修订The Little LISPer第三次,给了一个更加准确的名字The Little Schemer,和续集The Seasoned Schemer.
程序接受数据和产生数据。设计程序需要对数据有透彻的理解;好的程序反映了数据的结构。大多数数据和大多数程序是递归的。递归是定义一个对象或者靠自己解决解决一个问题的行为。
本书的目的是教会读者递归。第一个问题是使用何种程序来交流这种概念,三种选择:自然语言,如英语;正式数学;或者程序语言。自然语言时含混的不精确的,有时还笨拙冗长。这些是一般交流的优势,但是有时这对交流一些概念,如递归很不简洁。数学与自然语言相反:使用极少的符号就可以表达出强大且正式的想法。不幸的是,数学语言常常是隐蔽的,没有特殊训练几乎不能运用。技术和数学的联姻给我们第三中选择,一个几乎完美的选择:程序语言。我们认为程序语言时是最好的描述递归的方法。他们分享了数学给符号以正式意义的能力。但是与数学不同的是,程序语言是可以直接体验的——你可以拿着本书中的程序,观察他们的行为,修改他们,体验这些修改的效果。
也许教授递归的最好程序语言就是Scheme。Scheme语言本质上是符号性的——程序员不需要考虑他的自已的语言的符号之间的关系以及计算机中表示的关系。递归是Scheme天生的运行机制;程序的初始行为是(潜在的)创建递归定义。Scheme语言的实现主要是交互的,程序员可以立即参与和观察他的程序的行为。另外,这本书中最重要的是,Scheme程序的结构和这些程序操作的数据之间有着直接的对应。
尽管Scheme可以被描述的很正式,理解Scheme却不需要特别的数学角度。实际上,The Little Schemer 是基于向没有编程经历和承认不喜欢任何数学的学生在两周内介绍Scheme快速入门的演讲稿。许多这些同学准备公共事业作为职业。我们认为写Scheme的递归程序本质上就是简单的模式匹配。既然我们唯一考虑的是递归编程,我们仅仅限定处理Scheme特性的一些“为什么”:car, cdr, cons, eq?, null?, zero?, add1, sub1, number?, and, or, quote, lambda, define, 和cond。确实,我们的语言是理想化的Scheme。
The Little Schemer 和 The Seasoned Schemer将不会引导你实际的编程,但是掌握书中的这些概念会让你理解计算的本质。
阅读本书需要读者:认得字,认识数,会算术。
感谢***(略了)
导读
不要快速略读本书。要细细的读;有意义的提示散布在课文中。阅读本书不要少于3次settings。系统地读。如果你没有完全读懂一章,下一章你懂得更少。问题难度渐增;前边的问题不能解决,遇见后边的将束手无策。本书是以对话的形式套路你有趣的Scheme程序例子。如果你可以,读书的时候做作习题。Scheme是可用的。尽管Scheme的不同实现有微小的语法变化(主要是特殊函数的名称和domain的拼写),所有的Scheme都是一样的。为了使用Scheme,你需要定义atom?, sub1, 和add1。我们在The Little Schemer中介绍:
(define atom?
(lambda (x)
(and (not (pair? x)) (not (null? x)))))
为了找出你的Scheme是否定义了正确的atom?, 尝试(atom? (quote ()))然后确保它返回#f。实际上,这在现代Lisp,如Common Lisp中是自带的。为了使用Lisp,你还需要添加函数atom?:
(defun atom? (x)
(not (listp x)))
另外你需要做一些程序的修改。特别的,只需要微小的修改。如何尝试修改这些程序的建议在framenotes中。Framenotes中有“S:”的是Scheme相关的,那些有”L:”的是Lisp相关的。
第四章中我们将会从add1,sub1和zero?三种操作中获得基本的算术。Scheme本身没有提供add1和aub1,你必须用内建的基元定义加法和减法。为了避免circularity我们的算术加法和减法我们必须分别使用不同的符号:+和-。
在本书中我们没有给出任何的正式定义。我们认为你得到你自己的定义然后理解记忆他们比我们写给你的好。但是要确信使用前你得透彻理解规则。学习Scheme的关键是“模式匹配“,戒律指出了你看到过的模式。本书中初期,概念简化了;后期,概念得以拓展和限定。记住本树种所有的东西都是Scheme。Scheme本身具有一般普遍性,它包涵了远远多于我们书本中介绍的内容。你掌握了这本书后,就可以阅读更加综合性的Scheme书了。
我们整个的文本中使用了一些符号约定,主要是对不同类别的符号有字体的变化。变量和基本操作符的名称使用斜体。基本数据包括数和真假值是用sans serif。如define, lambda, cond, else, and, or和quote是粗体。当你尝试程序时注意framenotes而应忽略字体。为了突出字体的作用,framenotes中的程序使用打字机字体。当到第十章我们忽略这种字体的区分,在那里我们把程序和代码一视同仁。
最后,Webster把“punctuation”定义为“断句”行为;特别是,为了分隔语句和语句元素使其易懂明了,而使用标准标记来书写和打印的行为。我们已经从字面上采取了这一定义。为了使意思更清晰,我们已经放弃了一些熟悉的使用标点符号。具体来说,当在程序中时,我们丢弃在左栏标点符号的使用。
食品在我们的例子当中出现了很多次。首先,食物比起抽象符号更加容易形象化。(这书作为在消化的时候的读物可不适合 。可别吐一地:)我们希望食物可以帮助你理解我们使用的例子和概念。第二,我们想给你分分心。我们知道这门课程让人多沮丧,分心帮你保持理智。
你可以开始了。祝好运!我们希望你能够享受接下来的挑战。
Bon appetit !
Daniel P. Friedman
Matthias Felleisen