sicp每日一题[2.6]
1.sicp每日一题[1.42]2.sicp每日一题[1.43]3.sicp每日一题[1.44]4.sicp每日一题[1.45]5.sicp每日一题[1.46]6.sicp每日一题[2.1]7.sicp每日一题[2.2]8.sicp每日一题[2.3]9.sicp每日一题[2.4]10.sicp每日一题[2.5]
11.sicp每日一题[2.6]
12.sicp每日一题[2.7]13.sicp每日一题[2.8]14.sicp每日一题[2.9]15.sicp每日一题[2.11]16.sicp每日一题[2.10]17.sicp每日一题[2.12]18.sicp每日一题[2.13-2.16]19.sicp每日一题[2.17]20.sicp每日一题[2.18]21.sicp每日一题[2.19]22.sicp每日一题[2.20]23.sicp每日一题[2.21]24.sicp每日一题[2.22-2.23]25.sicp每日一题[2.24-2.27]26.sicp每日一题[2.28]27.sicp每日一题[2.29]28.sicp每日一题[2.30]29.sicp每日一题[2.31]30.sicp每日一题[2.32]31.sicp每日一题[2.33]32.sicp每日一题[2.34]33.sicp每日一题[2.35]34.sicp每日一题[2.36-2.37]35.sicp每日一题[2.38-2.39]36.sicp每日一题[2.40]37.sicp每日一题[2.41]38.sicp每日一题[2.42]39.sicp每日一题[2.43]40.sicp每日一题[2.44]41.sicp每日一题[2.45]42.sicp每日一题[2.46]43.sicp每日一题[2.47]44.sicp每日一题[2.48]45.sicp每日一题[2.49]46.sicp每日一题[2.50]47.sicp每日一题[2.51]48.sicp每日一题[2.52]49.sicp每日一题[2.53-2.55]50.sicp每日一题[2.56]51.sicp每日一题[2.57]52.sicp每日一题[2.58]53.sicp每日一题[2.59]54.sicp每日一题[2.60]55.sicp每日一题[2.61]56.sicp每日一题[2.62]57.sicp每日一题[2.63-2.64]58.sicp每日一题[2.65]59.sicp每日一题[2.66]60.sicp每日一题[2.67-2.68]61.sicp每日一题[2.69]62.sicp每日一题[2.70]63.sicp每日一题[2.71]64.sicp每日一题[2.72]65.sicp每日一题[2.73]66.sicp每日一题[2.74]67.sicp每日一题[2.75]68.sicp每日一题[2.76]69.sicp每日一题[2.77]70.sicp每日一题[2.78]71.sicp每日一题[2.79]72.sicp每日一题[2.80]73.sicp每日一题[2.81]74.sicp每日一题[2.82]75.sicp每日一题[2.83]76.sicp每日一题[2.84]77.sicp每日一题[2.85-2.86]Exercise2.6
In case representing pairs as procedures wasn't mind-boggling enough, consider that, in a language that can manipulate procedures, we can get by without numbers (at least insofar as nonnegative integers are concerned) by implementing 0 and the operation of adding 1 as
(define zero (lambda (f) (lambda (x) x)))
(define (add-1 n)
(lambda (f) (lambda (x) (f ((n f) x)))))
This representation is known as $Church numerals$, after its inventor, Alonzo Church, the logician who invented the λ calculus.
Define one and two directly (not in terms of zero and add-1). (Hint: Use substitution to evaluate(add-1 zero)
). Give a direct definition of the addition procedure + (not in terms of repeated application of add-1).
这个题太难理解了,题目里的两个函数,zero 我搞明白了,也勉强能接受它跟 0 的作用相同,但是我始终理解不了为啥 add-1 的作用是加一,明明是
(f x)
啊。
; 任何数加 0 都等于它本身。所以,表示 0 的函数,无论你给它传入什么函数 f 和参数 x,它都直接返回 x,相当于什么都不做。
; (lambda (f) ...) 定义了一个匿名函数,它接受一个函数 f 作为参数,并返回 (lambda (x) x)。
; (lambda (x) x) 定义了另一个匿名函数,它接受一个参数 x,并直接返回 x。
; 组合起来:zero 函数本质上就是一个恒等函数,无论你给它传入什么函数 f,它都会返回一个新的函数,这个新函数会直接返回它的输入 x。
; 这符合我们对 0 的理解————任何数加 0 等于它本身。
(define zero (lambda (f) (lambda (x) x)))
; 1. 把 (lambda (x) (square x)) 传给 zero 作为参数,返回新的函数 (lambda (x) x)
; 2. 再把 10 传给 (lambda (x) x),得到原数 10
(display ((zero (lambda (x) (square x))) 10)) ; 输出是 10
(newline)
; n 必须是 Church Numeral,比如说上面定义的 zero
; 返回值是一个新的 Church Numeral,表示的值为 n + 1
(define (add-1 n)
(lambda (f) (lambda (x) (f ((n f) x)))))
(display (((add-1 zero) square) 10)) ; 输出是 100
(newline)
; 1. 先用 f1 表示匿名函数 (lambda (x) (+ x 1)),则原式变为 ((zero f1) 0)
; 2. 把 zero 函数用它的定义替代,得到 (((lambda (f) (lambda (x) x)) f1) 0)
; 3. 把 f1 带入到 zero 的返回值函数,得到 ((lambda (x) x) 0)
; 4. (lambda (x) x) 函数会返回传入的参数,也就是0
((zero (lambda (x) (+ x 1))) 0) ; 输出是 0
; 1. 把 zero 作为参数传入,得到 (lambda (f) (lambda (x) (f ((zero f) x))))
; 2. 先处理 (zero f),根据上面我们对 zero 函数的分析,无论传入什么函数作为参数,它都返回 (lambda (x) x)
; 3. 则 ((zero f) x) 就是 x,(lambda (f) (lambda (x) (f x))),也就是无论传入什么 f 和 x,都会返回 (f x)
(define one (add-1 zero))
; 根据上面的分析,下面的程序相当于执行 ((lambda (x) (+ x 1)) 0), 也就是 0 + 1
((one (lambda (x) (+ x 1))) 0) ; 输出是 1
; 1. 把 one 作为参数传入,得到 (lambda (f) (lambda (x) (f ((one f) x))))
; 2. 根据上面的分析,((one f) x) 会返回 (f x)
; 3. 所以下面的函数无论传入什么 f 和 x,都会返回 (f (f x))
(define two (add-1 one))
; 根据上面的分析,下面的程序相当于执行 ((lambda (x) (+ x 1)) ((lambda (x) (+ x 1)) 0)), 也就是 ((0 + 1) + 1)
((two (lambda (x) (+ x 1))) 0) ; 输出是 2
; 以此类推,可以用如下方式直接定义 one, two, three
(define new-one (lambda (f) (lambda (x) (f x))))
(define new-two (lambda (f) (lambda (x) (f (f x)))))
(define three (lambda (f) (lambda (x) (f (f (f x))))))
; 虽然不理解为啥 add-1 可以表示加一,但是按照上面的规律,加法可以按下面的函数来定义
(define (add a b)
(lambda (f)
(lambda (x) ((a f) ((b f) x)))))
; 下面的程序相当于 ((two square) (square 2))
; 进一步替代得到 (square (square (square 2)))
(((add two one) square) 2) ; 输出是 256
; 执行结果
10
100
0
1
2
256
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· DeepSeek 开源周回顾「GitHub 热点速览」
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· AI与.NET技术实操系列(二):开始使用ML.NET
· 单线程的Redis速度为什么快?