我刚刚找到了以下lambda演算表达式:
(((λ f . (λ x . (f x))) (λ a . a)) (λ b . b))
这是一个函数,它接受一个参数f并返回另一个带有参数x的函数,并产生应用于f的x的结果。上述表达式的结果将是(λb.b)。
这让我想起部分应用和currying,但是“由内而外”的功能应用程序(f x)引起了我的兴趣。
这个表达有更深层次的理论意义吗?
答案 0 :(得分:8)
这个表达式实际上非常酷,即使它是一个非常简单的操作。毕竟,该功能只是功能应用,对吗?
这就是事情变得有趣的地方。在lambda演算中,应用程序是一个语法规则,它简单地说“如果f
是表达式而x
是表达式,则f x
是表达式”。应用程序不是任何类型的功能。这是不幸的:由于lambda演算完全与函数有关,因此必须严重依赖不是函数的东西!
你的榜样是对此的一种补救措施。虽然我们无法摆脱应用程序,但我们至少可以定义应用程序的对应物。对应的是lambda函数(λ f . (λ x . (f x)))
(或更具惯用性,λfx.f x
)。这个是一个函数,所以我们可以推理它并像其他任何函数一样使用它。我们可以将它作为参数传递给其他函数,也可以作为函数的结果使用。突然间,功能应用程序变得更加实用。
就像lambda演算一样,这就是我所拥有的一切,但是这个功能和其他类似功能在现实生活中也非常有用。在函数式编程语言F#中,这个函数甚至有一个名称,“管道向后运算符”,我们写它有中缀运算符<|
。因此,作为写f (x)
的替代方法,其中x
是表达式,我们可以编写f <| x
。这很好,因为它通常可以让我们免于编写很多恼人的括号。我试图在这里提出的关键点是,虽然一眼就看出你的例子似乎具有学术性,或者可能只是不太有用,但它实际上已经进入了几种主流编程语言。