我试图理解的一个问题包括:
twice (twice) f x , where twice == lambda f x . f (f x)
我正在努力了解如何进行替换,以及它意味着什么。
我的理解是(lambda x y.x + y)2 3 == 2 + 3 == 5.我不明白两次(两次)的意思,或f(f x)。
答案 0 :(得分:2)
两种观察方式。
你可以通过扩展twice
FX形式的任何子项来机械地解决这个问题 - 这个术语你最终将消除所有出现的两次,尽管你需要注意你真正理解的语法树lambda演算以避免错误。
twice
有两个参数,因此您的表达式twice (twice) f x
是应用于twice (twice) f
的redex x
。 (redex是一个子项,您可以独立于该术语的其余部分进行减少。)
在redex中扩展twice
的定义:twice (twice) f x -> twice (twice f)
。
将其替换为原始字词以获取twice (twice f) x
,这是另一个重新索引,我们可以展开twice
以获取twice f (twice f x)
(请注意此步骤中的括号)。
我们有两个twice
重新索引,我们可以在这里扩展,扩展括号内的一个稍微简单一点,给出twice f (f (f x))
,可以再次扩展为f (f (f (f x)))
。
你可以通过吸引更高阶的组合子来看到更直观的事情,“○”中缀组合器用于功能组合:
f ○ g = lambda x. f (g x)
很容易验证twice f x
和(f ○ f) x
是否扩展为相同的正常形式,即f (f x),
因此,我们有
twice f = f ○ f
使用这个,我们可以非常直接地扩展,首先取消twice
以支持组合组合:
twice (twice) f x
= (twice ○ twice) f x
= (twice (twice f)) x /* expand out '○' */
= (twice (f ○ f)) x
= ((f ○ f) ○ (f ○ f)) x
然后展开'○':
= (f ○ f) ((f ○ f) x)
= (f ○ f) (f (f x))
= (f (f (f (f x))))
这是更多的扩展步骤,因为我们首先扩展到包含'○'运算符的术语,然后扩展这些运算符,但步骤更简单,更直观,您不太可能误解您正在做什么。 '○'被广泛使用,是Haskell中的标准运算符,非常值得习惯。