stc-lang-1.0.0: src/Control/Monad/SD/Case.hs
module Control.Monad.SD.Case
( case_
, if_
) where
import Control.Monad
import Control.Monad.IO.Class
import Control.Monad.Par.Class as PC
import Control.Monad.SD.Ohua
import Data.StateElement
import Data.List as List
import Data.Maybe
case_ ::
forall a p. (NFData a, Show a, Eq p)
=> p
-> [(p, OhuaM a)]
-> OhuaM a
case_ cond patternsAndBranches = OhuaM moveState comp
where
moveState ::
forall ivar m. (ParIVar ivar m, MonadIO m)
=> GlobalState ivar
-> m (GlobalState ivar)
moveState gs =
(foldM (flip moveStateForward) gs . map snd) patternsAndBranches
comp ::
forall ivar m. (ParIVar ivar m, Monad m, MonadIO m, NFData (ivar S))
=> GlobalState ivar
-> m (a, GlobalState ivar)
comp gs
-- find the first pattern that matches
= do
let idx = List.findIndex ((cond ==) . fst) patternsAndBranches
let ith = fromMaybe (error "No pattern found for condition.") idx
-- one could of course do the following in parallel but it is not a performance bottleneck as of now.
let trueBranch = patternsAndBranches !! ith
let falseBranches =
((\(before, _:after) -> before ++ after) . List.splitAt ith)
patternsAndBranches
gs' <- foldM (flip moveStateForward) gs $ map snd falseBranches
(result, gs'') <- runOhua (snd trueBranch) gs'
return (result, gs'')
if_ :: (Show a, NFData a) => OhuaM Bool -> OhuaM a -> OhuaM a -> OhuaM a
if_ cond then_ else_ = do
i <- cond
case_ i [(True, then_), (False, else_)]