以下是一些不同语言的代码段。
有问题的函数double
来自SICP,例如。 1.41。
Lisp的:
(define (double f) (lambda (x) (f (f x))))
(define (inc x) (+ x 1))
(((double (double double)) inc) 5)
的Python:
def double(f):
def result(x):
return f(f(x))
return result
def inc(x):
return x + 1
double(double(double(inc)))(5)
使用Javascript:
var double = function(f) {
return function(x) { return f(f(x)) };
};
var inc = function(x) { return x + 1 };
(double(double(double(inc))))(5);
红宝石:
double = lambda {|f| lambda {|x| f[f[x]] } }
inc = lambda {|x| x+1 }
double[double[double[inc]]][5]
如果我不是疯了,这些函数应该做同样的事情并返回相同的结果。 但是,lisp版本返回21而其他版本返回13.你能解释一下这个区别吗?我错过了什么吗?
答案 0 :(得分:10)
如何调用方案代码中的函数与其他函数不同。等效的python是:
double(double(double))(inc)(5)
简而言之,方案代码创建了一个应用另一个函数16次的函数,并将该函数应用于inc
。 python创建的函数应用inc
8次;其他人的工作方式与python相同。
如果为中间步骤引入名称,差异可能会更清楚一些。在计划中:
(define quadruple (double double))
(define hexadecuple (double quadruple)) ; hexadecuple may not actually be a word...
(define add16 (hexadecuple inc))
(add16 5)
我希望这是正确的语法;自从我用方案做了一些事以来已经有一段时间了。
在python中:
add2 = double(inc)
add4 = double(add2)
add8 = double(add4)
add8(5)
答案 1 :(得分:2)
为了完整起见,这是一个固定的Ruby版本的样子:
double = ->f { ->x { f.(f.(x)) }}
inc = ->x { x.succ }
double.(double.(double)).(inc).(5)