Haskell复杂的函数组成

时间:2017-06-21 18:42:07

标签: haskell functional-programming

我试图在Haskell中学习函数组合。我有以下练习 我有函数:h x y = f (g x y),我需要找到与它相等的函数组合:

a) f . g  
b) (f.).g  
c) (.)f(.g)  
d) f(.g)

我知道(.)f g = f.g = f(g x)但我不理解这种复杂的功能构成

2 个答案:

答案 0 :(得分:4)

正确答案是(b)(f.).g

让我们分析一下这个功能。 (f.)部分是((.) f)的缩写,所以我们已经解决了这个问题,因此函数 - 没有语法糖 - 是:

(.) ((.) f) g

现在我们可以将第一个(.)函数重写为lambda表达式:

\x -> ((.) f) (g x)

现在当我们进一步评估左边的第二个函数(((.) f))时,我们得到:

\x -> (.) f (g x)

或:

\x -> f . g x

因此,如果我们在lambda表达式中转换(.)函数,我们得到:

\x -> (\y -> f ((g x) y))

现在我们可以使这个表达更优雅。 (g x) y可以重写为g x y

\x -> (\y -> f (g x y))

我们可以将嵌套的lambda表达式重写为单个lambda表达式:

\x y -> f (g x y)

这就是我们想要的。

答案 1 :(得分:3)

您也可以使用(.) (.) (.) - 尽管它有点challenging to understand,但评估会产生与您正在寻找的优雅形式相同的优雅形式

comp2 = (.) (.) (.)
comp2 f g x y == f (g x y)

评估(.) (.) (.)

-- comp
(.) = \f -> \g -> x -> f (g x)

-- evaluate
(.) (.) (.)
(\f -> \g -> \x -> f (g x)) (.) (.)
(\g -> \x -> (.) (g x)) (.)
\x -> (.) ((.) x)
\x -> (\f -> \g -> \x' -> f (g x')) ((.) x)
\x -> \g -> \x' -> ((.) x) (g x')
\x -> \g -> \x' -> ((\f -> \g' x'' -> f (g' x'')) x) (g x')
\x -> \g -> \x' -> (\g' -> \x'' -> x (g' x'')) (g x')
\x -> \g -> \x' -> \x'' -> x ((g x') x'')
\x -> \g -> \x' -> \x'' -> x (g x' x'')

-- alpha rename
\f -> \g -> \x -> \y -> f (g x y)

-- collapse lambdas 
\f g x y -> f (g x y)

了解(.)作品的模式

-- comp2
comp2 = (.) (.) (.)
comp2 f g x y == f (g x y)

-- comp3
comp3 = (.) (.) comp2
comp3 f g x y z == f (g x y z)

-- comp4
comp4 = (.) (.) comp3
comp4 f g w x y z == f (g w x y z)