haskell,链接过滤器

时间:2009-11-10 23:38:09

标签: haskell filter

将“map f(map g xs)”写成可以写入地图的单个调用

  

示例xs = map(f.g)xs

但你怎么写“过滤器p(过滤器q xs)”作为单个过滤器调用?点运算符似乎不适用于过滤器,就像它对地图一样。猜猜你会为谓词使用别的东西吗?

8 个答案:

答案 0 :(得分:9)

如果您定义了一个如下所示的函数both

both :: (a -> Bool) -> (a -> Bool) -> a -> Bool
both f g x = f x && g x

然后你可以写:

example xs = filter (both p q) xs

我不确定是否有标准功能可以帮助你......

答案 1 :(得分:8)

$ ghci
Prelude> :m +Control.Arrow
Prelude Control.Arrow> :t uncurry (&&) . ((0 <) &&& (< 10))
uncurry (&&) . ((0 <) &&& (< 10)) :: (Num a, Ord a) => a -> Bool
Prelude Control.Arrow> filter (uncurry (&&) . ((0 <) &&& (< 10))) [0..15]
[1,2,3,4,5,6,7,8,9]

或者宣布自己的运营商,如果你经常这样做的话。

infixr 3 &&:
p &&: q = \a -> p a && q a
infixr 2 ||:
p ||: q = \a -> p a || q a
not' = (.) not
all' = foldr (&&:) $ const True
any' = foldr (||:) $ const False

example xs = filter (p &&: q ||: not' r) xs

答案 2 :(得分:6)

为什么不进行列表理解?

example = [x | x <- xs, p x, q x]
-- for example
example = [x | x <- [1..10], (>3) x, x<5 ] -- [4]

答案 3 :(得分:4)

调用某些函数列表本质上是Control.Monad中ap函数的作用。然后你只需and结果。唯一的轻微丑陋是ap要求它们的参数都在同一个monad中(在这种情况下为List),所以我们需要用return组成它才能在这里工作。

import Control.Monad
filterByMany funcs = filter (and . ap funcs . return)

答案 4 :(得分:4)

我会定义一个lambda表达式。

module Main where

overTen :: Int -> Bool
overTen = (>10)

main :: IO ()
main = do
    print $ filter (\x -> overTen x && even x) [1..20]

输出:

$ ghci Test.hs
GHCi, version 6.10.4: http://www.haskell.org/ghc/  :? for help
Loading package ghc-prim ... linking ... done.
Loading package integer ... linking ... done.
Loading package base ... linking ... done.
[1 of 1] Compiling Main             ( Test.hs, interpreted )
Ok, modules loaded: Main.
*Main> main
[12,14,16,18,20]
*Main>

答案 5 :(得分:3)

import Data.Foldable
import Data.Monoid

p = (>4)
g = (<10)

main = print $ filter (getAll . foldMap (All.) [p,g]) [1..10]

输出

[5,6,7,8,9]

因为列表是可折叠的,您可以将谓词结果与All幺半群组合

答案 6 :(得分:2)

如下:

example xs = filter (forAll [p,q,r,s,t,u,v]) xs

forAll:: [(a -> Bool)] -> a -> Bool
forAll funcs x = all (map ($ x) funcs)

答案 7 :(得分:1)

我定义了一个辅助函数 - 这可能是以声明方式编写的,但我没有在此系统上安装GHCI进行测试:

allPredicates :: [a -> Bool] -> a -> Bool
allPredicates []     _ = True
allPredicates (p:ps) x = p x && allPredicates ps x

然后

filter (allPredicates [p, q]) xs