2017-03-18 13 views
2

我正在学习函数式编程。当我读到关于FP的lambda部分介绍时,我想到了一个问题。方案语言中的lambda语法

In Scheme the syntax for anonymous functions is the following one: 

(lambda (arg1...argn) body) 

... 

We can now easily define the compose function 

(define (compose f g) 
    (lambda (x) (f (g x)))) 

我努力去理解有关x,它不是在compose函数定义的参数列表。那么x如何传入?

另外,假设我们有功能g1采取参数y,z,如何拨打composecompose (f1 g1) y z?如果是这样,那么它不仅需要两个函数的参数,还需要来自g1的参数。我很困惑。

+0

'x'是结果组成的参数。假设你有函数'f1'和'g1'和参数'x1',那么你可以像这样调用'((compose f1 g1)x1)'。 – PetSerAl

回答

2

由于

(define (compose f g) 
    (lambda (x) (f (g x)))) 

我们

   (compose + *) 

评估为

   (lambda (x) (+ (* x))). 

也就是说,在

((compose + *) 42) 

我们得到

((compose + *) 42) 
=> ((lambda (x) (+ (* x))) 42) 
=> (+ (* 42)) 
=> (+ 42) 
=> 42 
1

首先在名字和参数周围有一个列表是语法糖。因此,要理解它完全可以充分展开:

(define compose 
    (lambda (f g)  ; compose 
    (lambda (x)  ; body 
     (f (g x)))) 

首先通知该名compose是考虑到外lambda表达式的评估的结果,就变成了双参数关闭。

所以,当您拨打(compose f2 f1)参数投注绑定到fg和身体表达(lambda (x) (f (g x)))进行了评估。它成为一个参数闭包。你可以在这里定义:

(define special-function (compose f2 f1)) 

为了使用该功能,你需要再次调用它。从而。 (special-function 5)将与评估(f2 (f1 5))相同。使用替代规则很容易看到。

那么为什么要这样呢?好。我们有一个需要的功能,像map和代替书写功能:

(map (lambda (x) (f2 (f1 x))) '(1 2 3 4)) 

你可以写

(map (compose f2 f1) '(1 2 3 4)) 

基本上是完全相同的表达更容易一些。

现实世界compose函数实际上可以接受任意数量的参数,它的最后一个参数是首先应用的函数,它将决定结果函数的参数。因此在球拍中你可以这样做:

((compose add1 add1 *) 3 7) 
; ==> 23