home *** CD-ROM | disk | FTP | other *** search
- -----------------------------------------------------------------------------
- -- Standard Library: Monad operations
- --
- -- Suitable for use with Hugs 98
- -----------------------------------------------------------------------------
-
- module Monad (
- MonadPlus(mzero, mplus),
- join, guard, when, unless, ap,
- msum,
- filterM, mapAndUnzipM, zipWithM, zipWithM_, foldM,
- liftM, liftM2, liftM3, liftM4, liftM5,
-
- -- ... and what the Prelude exports
- Monad((>>=), (>>), return, fail),
- Functor(fmap),
- mapM, mapM_, sequence, sequence_, (=<<),
- ) where
-
- -- The MonadPlus class definition
-
- class Monad m => MonadPlus m where
- mzero :: m a
- mplus :: m a -> m a -> m a
-
- -- Instances of MonadPlus
-
- instance MonadPlus Maybe where
- mzero = Nothing
- Nothing `mplus` ys = ys
- xs `mplus` ys = xs
-
- instance MonadPlus [ ] where
- mzero = []
- mplus = (++)
-
- -- Functions
-
- msum :: MonadPlus m => [m a] -> m a
- msum = foldr mplus mzero
-
- join :: (Monad m) => m (m a) -> m a
- join x = x >>= id
-
- when :: (Monad m) => Bool -> m () -> m ()
- when p s = if p then s else return ()
-
- unless :: (Monad m) => Bool -> m () -> m ()
- unless p s = when (not p) s
-
- ap :: (Monad m) => m (a -> b) -> m a -> m b
- ap = liftM2 ($)
-
- guard :: MonadPlus m => Bool -> m ()
- guard p = if p then return () else mzero
-
- mapAndUnzipM :: (Monad m) => (a -> m (b,c)) -> [a] -> m ([b], [c])
- mapAndUnzipM f xs = sequence (map f xs) >>= return . unzip
-
- zipWithM :: (Monad m) => (a -> b -> m c) -> [a] -> [b] -> m [c]
- zipWithM f xs ys = sequence (zipWith f xs ys)
-
- zipWithM_ :: (Monad m) => (a -> b -> m c) -> [a] -> [b] -> m ()
- zipWithM_ f xs ys = sequence_ (zipWith f xs ys)
-
- foldM :: (Monad m) => (a -> b -> m a) -> a -> [b] -> m a
- foldM f a [] = return a
- foldM f a (x:xs) = f a x >>= \ y -> foldM f y xs
-
- filterM :: Monad m => (a -> m Bool) -> [a] -> m [a]
- filterM p [] = return []
- filterM p (x:xs) = do b <- p x
- ys <- filterM p xs
- return (if b then (x:ys) else ys)
-
- liftM :: (Monad m) => (a -> b) -> (m a -> m b)
- liftM f = \a -> do { a' <- a; return (f a') }
-
- liftM2 :: (Monad m) => (a -> b -> c) -> (m a -> m b -> m c)
- liftM2 f = \a b -> do { a' <- a; b' <- b; return (f a' b') }
-
- liftM3 :: (Monad m) => (a -> b -> c -> d) ->
- (m a -> m b -> m c -> m d)
- liftM3 f = \a b c -> do { a' <- a; b' <- b; c' <- c;
- return (f a' b' c')}
-
- liftM4 :: (Monad m) => (a -> b -> c -> d -> e) ->
- (m a -> m b -> m c -> m d -> m e)
- liftM4 f = \a b c d -> do { a' <- a; b' <- b; c' <- c; d' <- d;
- return (f a' b' c' d')}
-
- liftM5 :: (Monad m) => (a -> b -> c -> d -> e -> f) ->
- (m a -> m b -> m c -> m d -> m e -> m f)
- liftM5 f = \a b c d e -> do { a' <- a; b' <- b; c' <- c; d' <- d;
- e' <- e; return (f a' b' c' d' e')}
-
- -----------------------------------------------------------------------------
-