我需要的类型的二进制组合子

(a -> Bool) -> (a -> Bool) -> a -> Bool

或也许

[a -> Bool] -> a -> Bool

(尽管这也只是第一的foldr1,我通常只需要组合两个布尔函数。)

这些是内置的?


如果不是,执行是简单的:

both f g x = f x && g x
either f g x = f x || g x

或也许

allF fs x = foldr (\ f b -> b && f x) True fs
anyF fs x = foldr (\ f b -> b || f x) False fs

Hoogle变成了什么,但有时其搜索无法正常一概而论。任何想法,如果这些内置的?他们可以从现有的库件建?

如果这些都没有内置,你可能会提出新的名字,因为这些名字是非常糟糕的。其实这是最主要的原因,我希望他们的的内置。

有帮助吗?

解决方案

Control.Monad限定instance Monad ((->) r),所以

ghci> :m Control.Monad
ghci> :t liftM2 (&&)
liftM2 (&&) :: (Monad m) => m Bool -> m Bool -> m Bool
ghci> liftM2 (&&) (5 <) (< 10) 8
True

您可以做同样的Control.Applicative.liftA2


不认真建议,但是...

ghci> :t (. flip ($)) . flip all
(. flip ($)) . flip all :: [a -> Bool] -> a -> Bool
ghci> :t (. flip ($)) . flip any
(. flip ($)) . flip any :: [a -> Bool] -> a -> Bool

其他提示

这不是一个内置,但我更喜欢替代方法是使用类型类为概括 布尔运算以任何元数的谓词:

module Pred2 where

class Predicate a where
  complement :: a -> a
  disjoin    :: a -> a -> a
  conjoin    :: a -> a -> a

instance Predicate Bool where
  complement = not
  disjoin    = (||)
  conjoin    = (&&)

instance (Predicate b) => Predicate (a -> b) where
  complement = (complement .)
  disjoin f g x = f x `disjoin` g x
  conjoin f g x = f x `conjoin` g x


-- examples:

ge :: Ord a => a -> a -> Bool
ge = complement (<)

pos = (>0)
nonzero = pos `disjoin` (pos . negate)
zero    = complement pos `conjoin` complement (pos . negate)

我爱哈斯克尔!

我不知道建宏,但我喜欢你提议的名字。

getCoolNumbers = filter $ either even (< 42)

可替换地,人们可以想到除了操作员符号类型类的替代品的。

getCoolNumbers = filter $ even <|> (< 42)
许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top