我正在尝试开始学习haskell,出现了一个问题。 比如说,我有一个函数
countFilter :: (a -> Bool) -> [a] -> ([a], Int)
countFilter a z = case z of [] -> ([], 0);
(x:xs) -> (filter a z , length (filter a z))
它返回一个列表,其中的所有项目都适用于某个谓词以及该列表的长度,这是不相关的。
countFilter (<7) [1,2,4,7,11,8,2]
将输出([1,2,4,2], 4)
.
如何创建这样的输出:([7,11,8], 4)
使用相同的谓词(<7)?
最佳答案
如果我正确理解您的问题,您希望返回所有不与谓词匹配的元素 (< 7)
作为该对的第一个元素。
在这种情况下,您可以简单地使用 not
函数翻转结果 bool 值。
IE。创建一个新谓词 (\x -> not (oldPred x))
,或使用函数组合:(not . oldPred)
:
countFilter :: (a -> Bool) -> [a] -> ([a], Int)
countFilter f xs = (filter (not . f) xs, length (filter f xs))
请注意,filter
和length
可以处理空列表,所以不需要写case
你自己。
或者,您可以使用 partition函数创建两个列表,这样您就不会过滤列表两次:
import Data.List
countFilter :: (a -> Bool) -> [a] -> ([a], Int)
countFilter f xs = let (ys, zs) = partition (not . f) xs
in (ys, length zs)
可能可以创建一个不使用 length
的更高效的版本。 ,但我把它作为练习:-)
关于list - 在 Haskell 中过滤列表,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3922983/