{- |
Module      :  ./Common/Lib/Maybe.hs
Description :  MaybeT monad transformer without the non-portable features
Copyright   :  C. Maeder and Uni Bremen 2002-2005
License     :  GPLv2 or higher, see LICENSE.txt

Maintainer  :  jonathan.von_schroeder@dfki.de
Stability   :  experimental
Portability :  portable

This module is a replacement of module Control.Monad.Maybe
and only contains the Monad instance for the newtype MaybeT m.

-}

module Common.Lib.Maybe (MaybeT (..), liftToMaybeT) where

import Control.Applicative ()
import Control.Monad
import qualified Control.Monad.Fail as Fail

-- | A monad transformer which adds Maybe semantics to an existing monad.
newtype MaybeT m a = MaybeT { MaybeT m a -> m (Maybe a)
runMaybeT :: m (Maybe a) }

instance Monad m => Functor (MaybeT m) where
  fmap :: (a -> b) -> MaybeT m a -> MaybeT m b
fmap = (a -> b) -> MaybeT m a -> MaybeT m b
forall (m :: * -> *) a1 r. Monad m => (a1 -> r) -> m a1 -> m r
liftM

instance Monad m => Applicative (MaybeT m) where
  pure :: a -> MaybeT m a
pure = a -> MaybeT m a
forall (m :: * -> *) a. Monad m => a -> m a
return
  <*> :: MaybeT m (a -> b) -> MaybeT m a -> MaybeT m b
(<*>) = MaybeT m (a -> b) -> MaybeT m a -> MaybeT m b
forall (m :: * -> *) a b. Monad m => m (a -> b) -> m a -> m b
ap

instance Monad m => Monad (MaybeT m) where
  return :: a -> MaybeT m a
return = m (Maybe a) -> MaybeT m a
forall (m :: * -> *) a. m (Maybe a) -> MaybeT m a
MaybeT (m (Maybe a) -> MaybeT m a)
-> (a -> m (Maybe a)) -> a -> MaybeT m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Maybe a -> m (Maybe a)
forall (m :: * -> *) a. Monad m => a -> m a
return (Maybe a -> m (Maybe a)) -> (a -> Maybe a) -> a -> m (Maybe a)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> Maybe a
forall a. a -> Maybe a
Just
  x :: MaybeT m a
x >>= :: MaybeT m a -> (a -> MaybeT m b) -> MaybeT m b
>>= f :: a -> MaybeT m b
f = m (Maybe b) -> MaybeT m b
forall (m :: * -> *) a. m (Maybe a) -> MaybeT m a
MaybeT (m (Maybe b) -> MaybeT m b) -> m (Maybe b) -> MaybeT m b
forall a b. (a -> b) -> a -> b
$ MaybeT m a -> m (Maybe a)
forall (m :: * -> *) a. MaybeT m a -> m (Maybe a)
runMaybeT MaybeT m a
x m (Maybe a) -> (Maybe a -> m (Maybe b)) -> m (Maybe b)
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= m (Maybe b) -> (a -> m (Maybe b)) -> Maybe a -> m (Maybe b)
forall b a. b -> (a -> b) -> Maybe a -> b
maybe (Maybe b -> m (Maybe b)
forall (m :: * -> *) a. Monad m => a -> m a
return Maybe b
forall a. Maybe a
Nothing) (MaybeT m b -> m (Maybe b)
forall (m :: * -> *) a. MaybeT m a -> m (Maybe a)
runMaybeT (MaybeT m b -> m (Maybe b))
-> (a -> MaybeT m b) -> a -> m (Maybe b)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> MaybeT m b
f)

instance Monad m => Fail.MonadFail (MaybeT m) where
  fail :: String -> MaybeT m a
fail _ = m (Maybe a) -> MaybeT m a
forall (m :: * -> *) a. m (Maybe a) -> MaybeT m a
MaybeT (m (Maybe a) -> MaybeT m a) -> m (Maybe a) -> MaybeT m a
forall a b. (a -> b) -> a -> b
$ Maybe a -> m (Maybe a)
forall (m :: * -> *) a. Monad m => a -> m a
return Maybe a
forall a. Maybe a
Nothing

liftToMaybeT :: Monad m => m a -> MaybeT m a
liftToMaybeT :: m a -> MaybeT m a
liftToMaybeT = m (Maybe a) -> MaybeT m a
forall (m :: * -> *) a. m (Maybe a) -> MaybeT m a
MaybeT (m (Maybe a) -> MaybeT m a)
-> (m a -> m (Maybe a)) -> m a -> MaybeT m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (a -> Maybe a) -> m a -> m (Maybe a)
forall (m :: * -> *) a1 r. Monad m => (a1 -> r) -> m a1 -> m r
liftM a -> Maybe a
forall a. a -> Maybe a
Just