10

我想定义一个函数来计算列表中满足给定谓词的元素数量:

  number_of_elements :: (a -> Bool) -> [a] -> Int
  number_of_elements f xs = length (filter f xs)

例如:

  number_of_elements (==2) [2,1,54,1,2]

应该返回2

我们可以写得更短:

  number_of_elements f = length . filter f

没有f参数可以写吗?

4

3 回答 3

17

是的:

number_of_elements = (length .) . filter
于 2011-12-23T22:07:02.193 回答
12

我认为您无法获得比您建议的更具可读性。但是,只是为了好玩,您可以这样做:

numberOfElements = (.) (.) (.) length filter

或者

(.:) = (.) . (.)
numberOfElements = length .: filter
于 2011-12-23T22:43:25.237 回答
7

您可能想了解语义编辑器组合器。从那里取出result组合器:

result :: (output -> output') -> (input -> output) -> (input -> output')
result = (.)

组合器接受一个函数并将其result应用于另一个函数的结果。现在,看看我们拥有的功能:

filter :: (a -> Bool) -> [a] -> [a]
length :: [a] -> Int

现在,length适用于[a]'s; 碰巧,它是表单函数的结果类型foo :: [a] -> [a]。所以,

result length :: ([a] -> [a]) -> ([a] -> Int)

但是 的结果filter恰好是一个[a] -> [a]函数,所以我们要应用于result length的结果filter

number_of_elements = result (result length) filter
于 2011-12-23T23:42:38.610 回答