最近一直在阅读《SICP》,而后下午作其中的习题2.6,对其题意很不理解,因而搜索了相关资料,不由如题设所说感到如雷灌顶,特此记录下来,以供你们阅读和交流html
若是以为将序对表示最为过程还不足以使人如雷灌顶,那么请考虑,在一个能够对程序作各种操做的语言中,咱们彻底能够没有数(至少在只考虑非整数的状况下),能够将0和加一操做实现为:wordpress
(define zero (lambda (f) (lambda (x) x))) (define (add-1 n) (lambda (f) (lambda (x) (f ((n f) x)))))
这一表现形式称为Church计数,名字来源于其发明人数理学家Church,请直接定义one和two(不使用zero和add-1)(提示:利用代换法去求值)。请给出加法过程+的一个直接定义(不要反复应用add-1)函数
说实话,我一直没有看懂题目中关于zero和add-1的定义,因而我搜索了相关资料。下边就结合资料谈一下它的概念。
首先要明确的是丘奇数中的zero,one等并不等同于数值上的0,1,2。你能够理解为它是零这个概念的一种表现形式。换句话说,它就是零的函数式表现形式。咱们先来看一下丘奇数中zero,one和two的表现形式code
(define zero (lambda (f) (lambda (x) x))) (define one (lambda (f) (lambda (x) (f x)))) (define two (lambda (f) (lambda (x) (f (f x)))))
咱们会发现zero,one和two都是一个函数,它接收(f)做为参数,其结果是一个接收(x)做为参数的函数。你们可能须要注意的是,(f)在这里显然也是一个函数,在LISP中函数是能够做为输入参数的。而后咱们会发现zero,one和two的区别好像就是(f)函数被使用的次数。zero中(f)没有被使用,one中(f)使用了一次,two中(f)使用了两次,对就是这个次数来表示0,1,2的概念。
咱们能够实验一下检验一下htm
(define (inc n) (+ n 1)) > ((zero inc) 0) 0 > ((zero inc) 1) 1 > ((one inc) 1) 2 > (((add-1 one) inc) 1) 3
咱们定义一个过程inc就是数值意义上的加一,而后使用zero,one和add-1发现确实如同咱们所想的,zero表示inc过程不会被使用,返回原数值;one表示inc被使用一次,返回加一的数值。three
咱们来使用替换法经过add-1和zero来求解one吧。get
(add-1 zero) ;展开add-1定义 (lambda (f) (lambda (x) (f ((zero f) x)))) ; 替换zero (lambda (f) (lambda (x) (f ((lambda (x) x) x)))) ; 简化由于((lambda (x) x) x)就等于x (lambda (f) (lambda (x) (f x)))
首先咱们要明白丘奇数加法的含义,咱们先记其加法为add-church,那么以下代码所示,最后一个过程得出的值应该是多少呢?class
> ((one inc) 1) 2 > ((two inc) 1) 3 > (((add-church one two) inc) 1) ?
根据猜想,应该是4吧。由于one表示inc对1这个数值使用一次,two标示使用两次,那么将两者加起来,那么就应该是three的含义啦,就是表示inc对1这个数值使用3次,那么就是4啦。
add-church的实现以下lambda
(define (add-church m n) (lambda (f) (lambda (x) ((m f) ((n f) x)))))
若是你将其与add-1进行对比,你会发现add-1中的f变成了(m f),若是吧add-1中的f记住(one f),你可能就会更加理解。那么你就会想add-m是如何标示的呢?搜索
参考资料
https://pfmiles.wordpress.com/2009/11/12/%E9%80%90%E6%AD%A5%E7%90%86%E8%A7%A3%E4%B8%98%E5%A5%87%E6%95%B0%E4%B8%80/
http://www.billthelizard.com/2010/10/sicp-26-church-numerals.html