{-|
Module      : Htcc.Utils.Bool
Description : Utilities of boolean
Copyright   : (c) roki, 2019
License     : MIT
Maintainer  : falgon53@yahoo.co.jp
Stability   : experimental
Portability : POSIX

Utilities of boolean
-}
{-# LANGUAGE ScopedTypeVariables #-}
module Htcc.Utils.Bool (
    -- * Boolean methods
    lor,
    land,
    sop,
    sopText
) where

import qualified Data.Text as T
import           Prelude   hiding (toInteger)

-- | For mappings \(f_i:X\to B\) to an element \(x\in X\) of a set \(X\), \(\displaystyle\bigvee_{i} f_i(x)\) where \(B\) is the boolean domain.
-- This function will stop evaluation when the result of \(f_i(x)\) is `True` (short circuit evaluation).
-- This is equivalent to:
--
-- > f1 x || f2 x || f3 x == lor [f1, f2, f3] x
lor :: [a -> Bool] -> a -> Bool
lor :: [a -> Bool] -> a -> Bool
lor [] _     = Bool
False
lor (f :: a -> Bool
f:fs :: [a -> Bool]
fs) x :: a
x | a -> Bool
f a
x = Bool
True | Bool
otherwise = [a -> Bool] -> a -> Bool
forall a. [a -> Bool] -> a -> Bool
lor [a -> Bool]
fs a
x

-- | For mappings \(f_i:X\to B\) to an element (\x\in X\) of a set \(X\), \(\displaystyle\bigwedge_{i} f_i(x)\) where \(B\) is the boolean domain.
-- This is equivalent to:
--
-- > f1 x && f2 x && f3 x == land [f1, f2, f3] x
land :: [a -> Bool] -> a -> Bool
land :: [a -> Bool] -> a -> Bool
land [] _     = Bool
False
land (f :: a -> Bool
f:fs :: [a -> Bool]
fs) x :: a
x = ((a -> Bool) -> Bool -> Bool) -> Bool -> [a -> Bool] -> Bool
forall (t :: * -> *) a b.
Foldable t =>
(a -> b -> b) -> b -> t a -> b
foldr (Bool -> Bool -> Bool
(&&) (Bool -> Bool -> Bool)
-> ((a -> Bool) -> Bool) -> (a -> Bool) -> Bool -> Bool
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ((a -> Bool) -> a -> Bool) -> a -> (a -> Bool) -> Bool
forall a b c. (a -> b -> c) -> b -> a -> c
flip (a -> Bool) -> a -> Bool
forall a. a -> a
id a
x) (a -> Bool
f a
x) [a -> Bool]
fs

-- | Sum of product form.
-- For mappings \(f_i:X\to B\) to an element \(x\in X\) of a set \(X\), \(\displaystyle\bigwedge_{j}\bigvee_{i} f_i(x_j)\) where \(B\) is the Boolean domain.
-- This function will stop evaluation when the result of \(f_i(x)\) is `True` (short circuit evaluation).
sop :: [a -> Bool] -> [a] -> Bool
sop :: [a -> Bool] -> [a] -> Bool
sop = (a -> Bool) -> [a] -> Bool
forall (t :: * -> *) a. Foldable t => (a -> Bool) -> t a -> Bool
all ((a -> Bool) -> [a] -> Bool)
-> ([a -> Bool] -> a -> Bool) -> [a -> Bool] -> [a] -> Bool
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [a -> Bool] -> a -> Bool
forall a. [a -> Bool] -> a -> Bool
lor

-- | The `T.Text` version of `sop`.
sopText :: [Char -> Bool] -> T.Text -> Bool
sopText :: [Char -> Bool] -> Text -> Bool
sopText = (Char -> Bool) -> Text -> Bool
T.all ((Char -> Bool) -> Text -> Bool)
-> ([Char -> Bool] -> Char -> Bool)
-> [Char -> Bool]
-> Text
-> Bool
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [Char -> Bool] -> Char -> Bool
forall a. [a -> Bool] -> a -> Bool
lor