2

我正在尝试编写一个函数,pipe它需要一个数学函数列表,pipe [f1,...,fn] x应该在哪里返回f1(f2(...(fn x))) 我已经将它设置为:

pipe :: [(a -> a)] -> (a -> a)
pipe fs   = foldLeft f base fs
  where
    f a x =    
    base  = 

-- >>> pipe [] 3
-- 3
--
-- >>> pipe [(\x -> x+x), (\x -> x + 3)] 3
-- 12
--
-- >>> pipe [(\x -> x * 4), (\x -> x + x)] 3
-- 24

使用 foldl 解决此问题的最佳方法是什么?谢谢!

4

2 回答 2

2

使用 foldl 它应该是:

pipe :: [(a -> a)] -> (a -> a)
pipe fs = foldl (\rs f -> f . rs) id fs 

或使用 eta:

pipe :: [(a -> a)] -> (a -> a)
pipe = foldl (\rs f -> f . rs) id 

与另一个 eta:

pipe :: [(a -> a)] -> (a -> a)
pipe = foldl (.) id 

以你为例:

pipe [(\x -> x * 4), (\x -> x + x)] 3
=> 24 
于 2019-11-07T01:34:41.333 回答
0

pipe实际上可以做得比你想象的要简单得多,而且没有必要使用相当低效的foldl(你甚至可以在自己的括号中看到这一点——它们是右结合的):just flip (foldr id). 到达那里的步骤:

pipe [f1,...,fn] x
f1 (f2 (... (fn x)))            -- your definition of pipe
id f1 (id f2 (... (id fn x)))   -- id x = x
foldr id x [f1,...,fn]          -- the definition of foldr
于 2019-11-07T02:53:47.990 回答