使用foldl实现Haskell的take功能 [英] Implementing Haskell's `take` function using `foldl`
问题描述
使用foldl
实现Haskell的take
和drop
函数.
Implementing Haskell's take
and drop
functions using foldl
.
关于如何使用foldl
??
take x ls = foldl ???
drop x ls = foldl ???
我尝试了这些,但是显示错误:
i've tried these but it's showing errors:
myFunc :: Int -> [a] -> [a]
myFunc n list = foldl func [] list
where
func x y | (length y) > n = x : y
| otherwise = y
发生错误:
*** Expression : foldl func [] list
*** Term : func
*** Type : a -> [a] -> [a]
*** Does not match : [a] -> [a] -> [a]
*** Because : unification would give infinite type
推荐答案
我注意到您从未指定折叠必须在提供的列表上方.因此,一种可能满足您问题的 letter 的方法是:
I note that you never specified the fold had to be over the supplied list. So, one approach that meets the letter of your question, though probably not the spirit, is:
sillytake :: Int -> [a] -> [a]
sillytake n xs = foldl go (const []) [1..n] xs
where go f _ (x:xs) = x : f xs
go _ _ [] = []
sillydrop :: Int -> [a] -> [a]
sillydrop n xs = foldl go id [1..n] xs
where go f _ (_:xs) = f xs
go _ _ [] = []
这些都使用左折,但在数字列表[1..n]
上-数字本身被忽略,并且仅使用列表的长度为其构建给定的自定义take n
或drop n
函数n
.然后,此功能将应用于原始提供的列表xs
.
These each use left folds, but over the list of numbers [1..n]
-- the numbers themselves are ignored, and the list is just used for its length to build a custom take n
or drop n
function for the given n
. This function is then applied to the original supplied list xs
.
这些版本在无限列表上都可以正常工作:
These versions work fine on infinite lists:
> sillytake 5 $ sillydrop 5 $ [1..]
[6,7,8,9,10]
这篇关于使用foldl实现Haskell的take功能的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!