packages feed

transformers 0.2.0.0 → 0.2.1.0

raw patch · 14 files changed

+519/−224 lines, 14 files

Files

Control/Monad/Trans/Cont.hs view
@@ -46,11 +46,14 @@ -} type Cont r = ContT r Identity +-- | Construct a continuation-passing computation from a function.+-- (The inverse of 'runCont'.) cont :: ((a -> r) -> r) -> Cont r a cont f = ContT (\ k -> Identity (f (runIdentity . k)))  -- | Runs a CPS computation, returns its result after applying the final -- continuation to it.+-- (The inverse of 'cont'.) runCont :: Cont r a	-- ^ continuation computation (@Cont@).     -> (a -> r)		-- ^ the final continuation, which produces 			-- the final result (often 'id').
Control/Monad/Trans/Error.hs view
@@ -15,6 +15,9 @@ A sequence of actions succeeds, producing a value, only if all the actions in the sequence are successful.  If one fails with an error, the rest of the sequence is skipped and the composite action fails with that error.++If the value of the error is not required, the variant in+"Control.Monad.Trans.Maybe" may be used instead. -}  module Control.Monad.Trans.Error (@@ -23,12 +26,15 @@     ErrorList(..),     ErrorT(..),     mapErrorT,+    -- * Error operations     throwError,     catchError,     -- * Lifting other operations     liftCallCC,     liftListen,     liftPass,+    -- * Examples+    -- $examples   ) where  import Control.Monad.IO.Class@@ -104,30 +110,22 @@             _       -> error "empty mfix argument"         in a -{- |-The error monad transformer. It can be used to add error handling to other-monads.--The @ErrorT@ Monad structure is parameterized over two things:-- * e - The error type.-- * m - The inner monad.--Here are some examples of use:--> -- wraps IO action that can throw an error e-> type ErrorWithIO e a = ErrorT e IO a-> ==> ErrorT (IO (Either e a))->-> -- IO monad wrapped in StateT inside of ErrorT-> type ErrorAndStateWithIO e s a = ErrorT e (StateT s IO) a-> ==> ErrorT (StateT s IO (Either e a))-> ==> ErrorT (StateT (s -> IO (Either e a,s)))--}-+-- | The error monad transformer. It can be used to add error handling+-- to other monads.+--+-- The @ErrorT@ Monad structure is parameterized over two things:+--+-- * e - The error type.+--+-- * m - The inner monad.+--+-- The 'return' function yields a successful computation, while @>>=@+-- sequences two subcomputations, failing on the first error. newtype ErrorT e m a = ErrorT { runErrorT :: m (Either e a) } +-- | Map the unwrapped computation using the given function.+--+-- * @'runErrorT' ('mapErrorT' f m) = f ('runErrorT' m@) mapErrorT :: (m (Either e a) -> n (Either e' b))           -> ErrorT e m a           -> ErrorT e' n b@@ -182,13 +180,18 @@ instance (Error e, MonadIO m) => MonadIO (ErrorT e m) where     liftIO = lift . liftIO --- | Signal an error+-- | Signal an error value @e@.+--+-- * @'runErrorT' ('throwErrorT' e) = 'return' ('Left' e)@ throwError :: (Monad m, Error e) => e -> ErrorT e m a throwError l = ErrorT $ return (Left l) --- | Handle an error+-- | Handle an error. catchError :: (Monad m, Error e) =>-    ErrorT e m a -> (e -> ErrorT e m a) -> ErrorT e m a+    ErrorT e m a                -- ^ the inner computation+    -> (e -> ErrorT e m a)      -- ^ a handler for errors in the inner+                                -- computation+    -> ErrorT e m a m `catchError` h = ErrorT $ do     a <- runErrorT m     case a of@@ -217,3 +220,15 @@     return $! case a of         Left  l      -> (Left  l, id)         Right (r, f) -> (Right r, f)++{- $examples++> -- wraps IO action that can throw an error e+> type ErrorWithIO e a = ErrorT e IO a+> ==> ErrorT (IO (Either e a))+>+> -- IO monad wrapped in StateT inside of ErrorT+> type ErrorAndStateWithIO e s a = ErrorT e (StateT s IO) a+> ==> ErrorT (StateT s IO (Either e a))+> ==> ErrorT (StateT (s -> IO (Either e a,s)))+-}
Control/Monad/Trans/List.hs view
@@ -9,8 +9,8 @@ -- Stability   :  experimental -- Portability :  portable ----- The List monad.---+-- The ListT monad transformer, adding backtracking to a given monad,+-- which must be commutative. -----------------------------------------------------------------------------  module Control.Monad.Trans.List (@@ -33,6 +33,9 @@ -- /Note:/ this does not yield a monad unless the argument monad is commutative. newtype ListT m a = ListT { runListT :: m [a] } +-- | Map between 'ListT' computations.+--+-- * @'runListT' ('mapListT' f m) = f ('runListT' m@) mapListT :: (m [a] -> n [b]) -> ListT m a -> ListT n b mapListT f m = ListT $ f (runListT m) 
Control/Monad/Trans/Maybe.hs view
@@ -8,7 +8,14 @@ -- Stability   :  experimental -- Portability :  portable ----- Declaration of the 'MaybeT' monad transformer.+-- The 'MaybeT' monad transformer adds the ability to fail to a monad.+--+-- A sequence of actions succeeds, producing a value, only if all the+-- actions in the sequence are successful.  If one fails, the rest of+-- the sequence is skipped and the composite action fails.+--+-- For a variant allowing a range of error values, see+-- "Control.Monad.Trans.Error". -----------------------------------------------------------------------------  module Control.Monad.Trans.Maybe (@@ -28,8 +35,16 @@ import Control.Applicative import Control.Monad (MonadPlus(mzero, mplus), liftM, ap) +-- | The parameterizable maybe monad, obtained by composing an arbitrary+-- monad with the 'Maybe' monad.+--+-- Computations are actions that may produce a value or fail.+--+-- The 'return' function yields a successful computation, while @>>=@+-- sequences two subcomputations, failing on the first error. newtype MaybeT m a = MaybeT { runMaybeT :: m (Maybe a) } +-- | Transform the computation inside a @MaybeT@. mapMaybeT :: (m (Maybe a) -> n (Maybe b)) -> MaybeT m a -> MaybeT n b mapMaybeT f = MaybeT . f . runMaybeT 
Control/Monad/Trans/RWS/Lazy.hs view
@@ -9,7 +9,9 @@ -- Stability   :  experimental -- Portability :  portable ----- Lazy RWS monad.+-- A monad transformer that combines 'ReaderT', 'WriterT' and 'StateT'.+-- This version is lazy; for a strict version, see+-- "Control.Monad.Trans.RWS.Strict", which has the same interface. -----------------------------------------------------------------------------  module Control.Monad.Trans.RWS.Lazy (@@ -34,8 +36,8 @@     -- * Writer operations     tell,     listen,-    pass,     listens,+    pass,     censor,     -- * State operations     get,@@ -57,11 +59,17 @@ import Control.Monad.Fix import Data.Monoid +-- | A monad containing an environment of type @r@, output of type @w@+-- and an updatable state of type @s@. type RWS r w s = RWST r w s Identity +-- | Construct an RWS computation from a function.+-- (The inverse of 'runRWS'.) rws :: (r -> s -> (a, s, w)) -> RWS r w s a rws f = RWST (\ r s -> Identity (f r s)) +-- | Unwrap an RWS computation as a function.+-- (The inverse of 'rws'.) runRWS :: RWS r w s a -> r -> s -> (a, s, w) runRWS m r s = runIdentity (runRWST m r s) @@ -82,8 +90,9 @@ withRWS = withRWST  -- ------------------------------------------------------------------------------ Our parameterizable RWS monad, with an inner monad-+-- | A monad transformer adding reading an environment of type @r@,+-- collecting an output of type @w@ and updating a state of type @s@+-- to an inner monad @m@. newtype RWST r w s m a = RWST { runRWST :: r -> s -> m (a, s, w) }  evalRWST :: (Monad m) => RWST r w s m a -> r -> s -> m (a, w)@@ -140,12 +149,15 @@ -- --------------------------------------------------------------------------- -- Reader operations +-- | Fetch the value of the environment. ask :: (Monoid w, Monad m) => RWST r w s m r ask = RWST $ \r s -> return (r, s, mempty) +-- | Execute a computation in a modified environment local :: (Monoid w, Monad m) => (r -> r) -> RWST r w s m a -> RWST r w s m a local f m = RWST $ \r s -> runRWST m (f r) s +-- | Retrieve a function of the current environment. asks :: (Monoid w, Monad m) => (r -> a) -> RWST r w s m a asks f = do     r <- ask@@ -154,24 +166,39 @@ -- --------------------------------------------------------------------------- -- Writer operations +-- | @'tell' w@ is an action that produces the output @w@. tell :: (Monoid w, Monad m) => w -> RWST r w s m () tell w = RWST $ \_ s -> return ((),s,w) +-- | @'listen' m@ is an action that executes the action @m@ and adds its+-- output to the value of the computation. listen :: (Monoid w, Monad m) => RWST r w s m a -> RWST r w s m (a, w) listen m = RWST $ \r s -> do     ~(a, s', w) <- runRWST m r s     return ((a, w), s', w) +-- | @'listens' f m@ is an action that executes the action @m@ and adds+-- the result of applying @f@ to the output to the value of the computation.+--+-- * @'listens' f m = 'liftM' (id *** f) ('listen' m)@+listens :: (Monoid w, Monad m) => (w -> b) -> RWST r w s m a -> RWST r w s m (a, b)+listens f m = do+    ~(a, w) <- listen m+    return (a, f w)++-- | @'pass' m@ is an action that executes the action @m@, which returns+-- a value and a function, and returns the value, applying the function+-- to the output. pass :: (Monoid w, Monad m) => RWST r w s m (a, w -> w) -> RWST r w s m a pass m = RWST $ \r s -> do     ~((a, f), s', w) <- runRWST m r s     return (a, s', f w) -listens :: (Monoid w, Monad m) => (w -> b) -> RWST r w s m a -> RWST r w s m (a, b)-listens f m = do-    ~(a, w) <- listen m-    return (a, f w)- +-- | @'censor' f m@ is an action that executes the action @m@ and+-- applies the function @f@ to its output, leaving the return value+-- unchanged.+--+-- * @'censor' f m = 'pass' ('liftM' (\\x -> (x,f)) m)@ censor :: (Monoid w, Monad m) => (w -> w) -> RWST r w s m a -> RWST r w s m a censor f m = pass $ do     a <- m@@ -180,25 +207,25 @@ -- --------------------------------------------------------------------------- -- State operations +-- | Fetch the current value of the state within the monad. get :: (Monoid w, Monad m) => RWST r w s m s get = RWST $ \_ s -> return (s, s, mempty) +-- | @'put' s@ sets the state within the monad to @s@. put :: (Monoid w, Monad m) => s -> RWST r w s m () put s = RWST $ \_ _ -> return ((), s, mempty) --- | Monadic state transformer.------      Maps an old state to a new state inside a state monad.---      The old state is thrown away.---+-- | @'modify' f@ is an action that updates the state to the result of+-- applying @f@ to the current state. modify :: (Monoid w, Monad m) => (s -> s) -> RWST r w s m () modify f = do     s <- get     put (f s)  --- | Gets specific component of the state, using a projection function+-- | Get a specific component of the state, using a projection function -- supplied.-+--+-- * @'gets' f = 'liftM' f 'get'@ gets :: (Monoid w, Monad m) => (s -> a) -> RWST r w s m a gets f = do     s <- get
Control/Monad/Trans/RWS/Strict.hs view
@@ -9,7 +9,9 @@ -- Stability   :  experimental -- Portability :  portable ----- Strict RWS monad.+-- A monad transformer that combines 'ReaderT', 'WriterT' and 'StateT'.+-- This version is strict; for a lazy version, see+-- "Control.Monad.Trans.RWS.Lazy", which has the same interface. -----------------------------------------------------------------------------  module Control.Monad.Trans.RWS.Strict (@@ -34,8 +36,8 @@     -- * Writer operations     tell,     listen,-    pass,     listens,+    pass,     censor,     -- * State operations     get,@@ -57,11 +59,17 @@ import Control.Monad.Fix import Data.Monoid +-- | A monad containing an environment of type @r@, output of type @w@+-- and an updatable state of type @s@. type RWS r w s = RWST r w s Identity +-- | Construct an RWS computation from a function.+-- (The inverse of 'runRWS'.) rws :: (r -> s -> (a, s, w)) -> RWS r w s a rws f = RWST (\ r s -> Identity (f r s)) +-- | Unwrap an RWS computation as a function.+-- (The inverse of 'rws'.) runRWS :: RWS r w s a -> r -> s -> (a, s, w) runRWS m r s = runIdentity (runRWST m r s) @@ -82,8 +90,9 @@ withRWS = withRWST  -- ------------------------------------------------------------------------------ Our parameterizable RWS monad, with an inner monad-+-- | A monad transformer adding reading an environment of type @r@,+-- collecting an output of type @w@ and updating a state of type @s@+-- to an inner monad @m@. newtype RWST r w s m a = RWST { runRWST :: r -> s -> m (a, s, w) }  evalRWST :: (Monad m) => RWST r w s m a -> r -> s -> m (a, w)@@ -140,12 +149,15 @@ -- --------------------------------------------------------------------------- -- Reader operations +-- | Fetch the value of the environment. ask :: (Monoid w, Monad m) => RWST r w s m r ask = RWST $ \r s -> return (r, s, mempty) +-- | Execute a computation in a modified environment local :: (Monoid w, Monad m) => (r -> r) -> RWST r w s m a -> RWST r w s m a local f m = RWST $ \r s -> runRWST m (f r) s +-- | Retrieve a function of the current environment. asks :: (Monoid w, Monad m) => (r -> a) -> RWST r w s m a asks f = do     r <- ask@@ -154,24 +166,39 @@ -- --------------------------------------------------------------------------- -- Writer operations +-- | @'tell' w@ is an action that produces the output @w@. tell :: (Monoid w, Monad m) => w -> RWST r w s m () tell w = RWST $ \_ s -> return ((),s,w) +-- | @'listen' m@ is an action that executes the action @m@ and adds its+-- output to the value of the computation. listen :: (Monoid w, Monad m) => RWST r w s m a -> RWST r w s m (a, w) listen m = RWST $ \r s -> do     (a, s', w) <- runRWST m r s     return ((a, w), s', w) +-- | @'listens' f m@ is an action that executes the action @m@ and adds+-- the result of applying @f@ to the output to the value of the computation.+--+-- * @'listens' f m = 'liftM' (id *** f) ('listen' m)@+listens :: (Monoid w, Monad m) => (w -> b) -> RWST r w s m a -> RWST r w s m (a, b)+listens f m = do+    (a, w) <- listen m+    return (a, f w)++-- | @'pass' m@ is an action that executes the action @m@, which returns+-- a value and a function, and returns the value, applying the function+-- to the output. pass :: (Monoid w, Monad m) => RWST r w s m (a, w -> w) -> RWST r w s m a pass m = RWST $ \r s -> do     ((a, f), s', w) <- runRWST m r s     return (a, s', f w) -listens :: (Monoid w, Monad m) => (w -> b) -> RWST r w s m a -> RWST r w s m (a, b)-listens f m = do-    (a, w) <- listen m-    return (a, f w)- +-- | @'censor' f m@ is an action that executes the action @m@ and+-- applies the function @f@ to its output, leaving the return value+-- unchanged.+--+-- * @'censor' f m = 'pass' ('liftM' (\\x -> (x,f)) m)@ censor :: (Monoid w, Monad m) => (w -> w) -> RWST r w s m a -> RWST r w s m a censor f m = pass $ do     a <- m@@ -180,25 +207,25 @@ -- --------------------------------------------------------------------------- -- State operations +-- | Fetch the current value of the state within the monad. get :: (Monoid w, Monad m) => RWST r w s m s get = RWST $ \_ s -> return (s, s, mempty) +-- | @'put' s@ sets the state within the monad to @s@. put :: (Monoid w, Monad m) => s -> RWST r w s m () put s = RWST $ \_ _ -> return ((), s, mempty) --- | Monadic state transformer.------      Maps an old state to a new state inside a state monad.---      The old state is thrown away.---+-- | @'modify' f@ is an action that updates the state to the result of+-- applying @f@ to the current state. modify :: (Monoid w, Monad m) => (s -> s) -> RWST r w s m () modify f = do     s <- get     put (f s)  --- | Gets specific component of the state, using a projection function+-- | Get a specific component of the state, using a projection function -- supplied.-+--+-- * @'gets' f = 'liftM' f 'get'@ gets :: (Monoid w, Monad m) => (s -> a) -> RWST r w s m a gets f = do     s <- get
Control/Monad/Trans/State.hs view
@@ -9,7 +9,15 @@ -- Stability   :  experimental -- Portability :  portable ----- State monads.+-- State monads, passing an updateable state through a computation.+--+-- Some computations may not require the full power of state transformers:+--+-- * For a read-only state, see "Control.Monad.Trans.Reader".+--+-- * To accumulate a value without using it on the way, see+--   "Control.Monad.Trans.Writer".+-- -- This version is lazy; for a strict version, see -- "Control.Monad.Trans.State.Strict", which has the same interface. -----------------------------------------------------------------------------
Control/Monad/Trans/State/Lazy.hs view
@@ -10,15 +10,18 @@ -- Portability :  portable -- -- Lazy state monads, passing an updateable state through a computation.+-- See below for examples. ----- Some computations may not require the full power if state transformers:+-- In this version, sequencing of computations is lazy in the state.+-- For a strict version, see "Control.Monad.Trans.Writer.Strict", which+-- has the same interface. --+-- Some computations may not require the full power of state transformers:+-- -- * For a read-only state, see "Control.Monad.Trans.Reader". -- -- * To accumulate a value without using it on the way, see --   "Control.Monad.Trans.Writer".------ See below for examples. -----------------------------------------------------------------------------  module Control.Monad.Trans.State.Lazy (@@ -48,7 +51,14 @@     liftListen,     liftPass,     -- * Examples+    -- ** State monads     -- $examples++    -- ** Counting+    -- $counting++    -- ** Labelling trees+    -- $labelling   ) where  import Control.Monad.IO.Class@@ -60,9 +70,11 @@ import Control.Monad.Fix  -- ------------------------------------------------------------------------------ | A parameterizable state monad where @s@ is the type of the state--- to carry.-+-- | A state monad parameterized by the type @s@ of the state to carry.+--+-- The 'return' function leaves the state unchanged, while @>>=@ uses+-- the final state of the first computation as the initial state of+-- the second. type State s = StateT s Identity  -- | Construct a state monad computation from a function.@@ -81,7 +93,7 @@ -- | Evaluate a state computation with the given initial state -- and return the final value, discarding the final state. ----- @'evalState' m s = 'fst' ('runState' m s)@+-- * @'evalState' m s = 'fst' ('runState' m s)@ evalState :: State s a  -- ^state-passing computation to execute           -> s          -- ^initial value           -> a          -- ^return value of the state computation@@ -90,66 +102,42 @@ -- | Evaluate a state computation with the given initial state -- and return the final state, discarding the final value. ----- @'execState' m s = 'snd' ('runState' m s)@+-- * @'execState' m s = 'snd' ('runState' m s)@ execState :: State s a  -- ^state-passing computation to execute           -> s          -- ^initial value           -> s          -- ^final state execState m s = snd (runState m s) --- |Map a stateful computation from one (return value, state) pair to--- another.  For instance, to convert numberTree from a function that--- returns a tree to a function that returns the sum of the numbered--- tree (see the Examples section for numberTree and sumTree) you may--- write:+-- | Map both the return value and final state of a computation using+-- the given function. ----- > sumNumberedTree :: (Eq a) => Tree a -> State (Table a) Int--- > sumNumberedTree = mapState (\ (t, tab) -> (sumTree t, tab))  . numberTree-+-- * @'runState' ('mapState' f m) = f . 'runState' m@ mapState :: ((a, s) -> (b, s)) -> State s a -> State s b mapState f = mapStateT (Identity . f . runIdentity) --- |Apply this function to this state and return the resulting state.+-- | @'withState' f m@ executes action @m@ on a state modified by+-- applying @f@.+--+-- * @'withState' f m = 'modify' f >> m@ withState :: (s -> s) -> State s a -> State s a withState = withStateT  -- ------------------------------------------------------------------------------ | A parameterizable state monad for encapsulating an inner--- monad.------ The StateT Monad structure is parameterized over two things:------   * s - The state.------   * m - The inner monad.------ Here are some examples of use:------ (Parser from ParseLib with Hugs)+-- | A state transformer monad parameterized by: ----- >  type Parser a = StateT String [] a--- >     ==> StateT (String -> [(a,String)])+--   * @s@ - The state. ----- For example, item can be written as:+--   * @m@ - The inner monad. ----- >   item = do (x:xs) <- get--- >          put xs--- >          return x--- >--- >   type BoringState s a = StateT s Identity a--- >        ==> StateT (s -> Identity (a,s))--- >--- >   type StateWithIO s a = StateT s IO a--- >        ==> StateT (s -> IO (a,s))--- >--- >   type StateWithErr s a = StateT s Maybe a--- >        ==> StateT (s -> Maybe (a,s))-+-- The 'return' function leaves the state unchanged, while @>>=@ uses+-- the final state of the first computation as the initial state of+-- the second. newtype StateT s m a = StateT { runStateT :: s -> m (a,s) }  -- | Evaluate a state computation with the given initial state -- and return the final value, discarding the final state. ----- @'evalStateT' m s = 'liftM' 'fst' ('runStateT' m s)@+-- * @'evalStateT' m s = 'liftM' 'fst' ('runStateT' m s)@ evalStateT :: (Monad m) => StateT s m a -> s -> m a evalStateT m s = do     ~(a, _) <- runStateT m s@@ -158,25 +146,23 @@ -- | Evaluate a state computation with the given initial state -- and return the final state, discarding the final value. ----- @'execStateT' m s = 'liftM' 'snd' ('runStateT' m s)@+-- * @'execStateT' m s = 'liftM' 'snd' ('runStateT' m s)@ execStateT :: (Monad m) => StateT s m a -> s -> m s execStateT m s = do     ~(_, s') <- runStateT m s     return s' --- | Map a stateful computation from one (return value, state) pair to--- another.  For instance, to convert numberTree from a function that--- returns a tree to a function that returns the sum of the numbered--- tree (see the Examples section for numberTree and sumTree) you may--- write:+-- | Map both the return value and final state of a computation using+-- the given function. ----- > sumNumberedTree :: (Eq a) => Tree a -> State (Table a) Int--- > sumNumberedTree = mapState (\ (t, tab) -> (sumTree t, tab))  . numberTree-+-- * @'runStateT' ('mapStateT' f m) = f . 'runStateT' m@ mapStateT :: (m (a, s) -> n (b, s)) -> StateT s m a -> StateT s n b mapStateT f m = StateT $ f . runStateT m --- | Apply this function to this state and return the resulting state.+-- | @'withStateT' f m@ executes action @m@ on a state modified by+-- applying @f@.+--+-- * @'withStateT' f m = 'modify' f >> m@ withStateT :: (s -> s) -> StateT s m a -> StateT s m a withStateT f m = StateT $ runStateT m . f @@ -222,11 +208,8 @@ put :: (Monad m) => s -> StateT s m () put s = StateT $ \_ -> return ((), s) --- | Monadic state transformer.------      Maps an old state to a new state inside a state monad.---      The old state is thrown away.-+-- | @'modify' f@ is an action that updates the state to the result of+-- applying @f@ to the current state. modify :: (Monad m) => (s -> s) -> StateT s m () modify f = do     s <- get@@ -234,7 +217,8 @@  -- | Get a specific component of the state, using a projection function -- supplied.-+--+-- * @'gets' f = 'liftM' f 'get'@ gets :: (Monad m) => (s -> a) -> StateT s m a gets f = do     s <- get@@ -280,6 +264,30 @@  {- $examples +Parser from ParseLib with Hugs:++> type Parser a = StateT String [] a+>    ==> StateT (String -> [(a,String)])++For example, item can be written as:++> item = do (x:xs) <- get+>        put xs+>        return x+>+> type BoringState s a = StateT s Identity a+>      ==> StateT (s -> Identity (a,s))+>+> type StateWithIO s a = StateT s IO a+>      ==> StateT (s -> IO (a,s))+>+> type StateWithErr s a = StateT s Maybe a+>      ==> StateT (s -> Maybe (a,s))++-}++{- $counting+ A function to increment a counter.  Taken from the paper /Generalising Monads to Arrows/, John Hughes (<http://www.math.chalmers.se/~rjmh/>), November 1998:@@ -299,6 +307,10 @@ > plus :: Int -> Int -> Int > plus n x = execState (sequence $ replicate n tick) x +-}++{- $labelling+ An example from /The Craft of Functional Programming/, Simon Thompson (<http://www.cs.kent.ac.uk/people/staff/sjt/>), Addison-Wesley 1999: \"Given an arbitrary tree, transform it to a@@ -351,4 +363,5 @@ > sumTree :: (Num a) => Tree a -> a > sumTree Nil = 0 > sumTree (Node e t1 t2) = e + (sumTree t1) + (sumTree t2)+ -}
Control/Monad/Trans/State/Strict.hs view
@@ -9,9 +9,19 @@ -- Stability   :  experimental -- Portability :  portable ----- Strict state monads.---+-- Strict state monads, passing an updateable state through a computation. -- See below for examples.+--+-- In this version, sequencing of computations is strict in the state.+-- For a lazy version, see "Control.Monad.Trans.Writer.Lazy", which+-- has the same interface.+--+-- Some computations may not require the full power of state transformers:+--+-- * For a read-only state, see "Control.Monad.Trans.Reader".+--+-- * To accumulate a value without using it on the way, see+--   "Control.Monad.Trans.Writer". -----------------------------------------------------------------------------  module Control.Monad.Trans.State.Strict (@@ -41,106 +51,93 @@     liftListen,     liftPass,     -- * Examples+    -- ** State monads     -- $examples++    -- ** Counting+    -- $counting++    -- ** Labelling trees+    -- $labelling   ) where -import Data.Functor.Identity import Control.Monad.IO.Class import Control.Monad.Trans.Class+import Data.Functor.Identity  import Control.Applicative import Control.Monad import Control.Monad.Fix  -- ------------------------------------------------------------------------------ | A parameterizable state monad where /s/ is the type of the state--- to carry and /a/ is the type of the /return value/.-+-- | A state monad parameterized by the type @s@ of the state to carry.+--+-- The 'return' function leaves the state unchanged, while @>>=@ uses+-- the final state of the first computation as the initial state of+-- the second. type State s = StateT s Identity  -- | Construct a state monad computation from a function. -- (The inverse of 'runState'.)-state :: (s -> (a, s)) -> State s a+state :: (s -> (a, s))  -- ^pure state transformer+      -> State s a      -- ^equivalent state-passing computation state f = StateT (Identity . f)  -- | Unwrap a state monad computation as a function. -- (The inverse of 'state'.)-runState :: State s a -> s -> (a, s)+runState :: State s a   -- ^state-passing computation to execute+         -> s           -- ^initial state+         -> (a, s)      -- ^return value and final state runState m = runIdentity . runStateT m --- |Evaluate this state monad with the given initial state,throwing--- away the final state.  Very much like @fst@ composed with--- @runstate@.--evalState :: State s a -- ^The state to evaluate-          -> s         -- ^An initial value-          -> a         -- ^The return value of the state application+-- | Evaluate a state computation with the given initial state+-- and return the final value, discarding the final state.+--+-- * @'evalState' m s = 'fst' ('runState' m s)@+evalState :: State s a  -- ^state-passing computation to execute+          -> s          -- ^initial value+          -> a          -- ^return value of the state computation evalState m s = fst (runState m s) --- |Execute this state and return the new state, throwing away the--- return value.  Very much like @snd@ composed with--- @runstate@.--execState :: State s a -- ^The state to evaluate-          -> s         -- ^An initial value-          -> s         -- ^The new state+-- | Evaluate a state computation with the given initial state+-- and return the final state, discarding the final value.+--+-- * @'execState' m s = 'snd' ('runState' m s)@+execState :: State s a  -- ^state-passing computation to execute+          -> s          -- ^initial value+          -> s          -- ^final state execState m s = snd (runState m s) --- |Map a stateful computation from one (return value, state) pair to--- another.  For instance, to convert numberTree from a function that--- returns a tree to a function that returns the sum of the numbered--- tree (see the Examples section for numberTree and sumTree) you may--- write:+-- | Map both the return value and final state of a computation using+-- the given function. ----- > sumNumberedTree :: (Eq a) => Tree a -> State (Table a) Int--- > sumNumberedTree = mapState (\ (t, tab) -> (sumTree t, tab))  . numberTree-+-- * @'runState' ('mapState' f m) = f . 'runState' m@ mapState :: ((a, s) -> (b, s)) -> State s a -> State s b mapState f = mapStateT (Identity . f . runIdentity) --- |Apply this function to this state and return the resulting state.+-- | @'withState' f m@ executes action @m@ on a state modified by+-- applying @f@.+--+-- * @'withState' f m = 'modify' f >> m@ withState :: (s -> s) -> State s a -> State s a withState = withStateT  -- ------------------------------------------------------------------------------ | A parameterizable state monad for encapsulating an inner--- monad.------ The StateT Monad structure is parameterized over two things:------   * s - The state.------   * m - The inner monad.------ Here are some examples of use:------ (Parser from ParseLib with Hugs)+-- | A state transformer monad parameterized by: ----- >  type Parser a = StateT String [] a--- >     ==> StateT (String -> [(a,String)])+--   * @s@ - The state. ----- For example, item can be written as:+--   * @m@ - The inner monad. ----- >   item = do (x:xs) <- get--- >          put xs--- >          return x--- >--- >   type BoringState s a = StateT s Identity a--- >        ==> StateT (s -> Identity (a,s))--- >--- >   type StateWithIO s a = StateT s IO a--- >        ==> StateT (s -> IO (a,s))--- >--- >   type StateWithErr s a = StateT s Maybe a--- >        ==> StateT (s -> Maybe (a,s))-+-- The 'return' function leaves the state unchanged, while @>>=@ uses+-- the final state of the first computation as the initial state of+-- the second. newtype StateT s m a = StateT { runStateT :: s -> m (a,s) }  -- | Evaluate a state computation with the given initial state -- and return the final value, discarding the final state. ----- @'evalStateT' m s = 'liftM' 'fst' ('runStateT' m s)@-+-- * @'evalStateT' m s = 'liftM' 'fst' ('runStateT' m s)@ evalStateT :: (Monad m) => StateT s m a -> s -> m a evalStateT m s = do     (a, _) <- runStateT m s@@ -149,25 +146,23 @@ -- | Evaluate a state computation with the given initial state -- and return the final state, discarding the final value. ----- @'execStateT' m s = 'liftM' 'snd' ('runStateT' m s)@+-- * @'execStateT' m s = 'liftM' 'snd' ('runStateT' m s)@ execStateT :: (Monad m) => StateT s m a -> s -> m s execStateT m s = do     (_, s') <- runStateT m s     return s' --- | Map a stateful computation from one (return value, state) pair to--- another.  For instance, to convert numberTree from a function that--- returns a tree to a function that returns the sum of the numbered--- tree (see the Examples section for numberTree and sumTree) you may--- write:+-- | Map both the return value and final state of a computation using+-- the given function. ----- > sumNumberedTree :: (Eq a) => Tree a -> State (Table a) Int--- > sumNumberedTree = mapState (\ (t, tab) -> (sumTree t, tab))  . numberTree-+-- * @'runStateT' ('mapStateT' f m) = f . 'runStateT' m@ mapStateT :: (m (a, s) -> n (b, s)) -> StateT s m a -> StateT s n b mapStateT f m = StateT $ f . runStateT m --- | Apply this function to this state and return the resulting state.+-- | @'withStateT' f m@ executes action @m@ on a state modified by+-- applying @f@.+--+-- * @'withStateT' f m = 'modify' f >> m@ withStateT :: (s -> s) -> StateT s m a -> StateT s m a withStateT f m = StateT $ runStateT m . f @@ -205,25 +200,25 @@ instance (MonadIO m) => MonadIO (StateT s m) where     liftIO = lift . liftIO +-- | Fetch the current value of the state within the monad. get :: (Monad m) => StateT s m s get = StateT $ \s -> return (s, s) +-- | @'put' s@ sets the state within the monad to @s@. put :: (Monad m) => s -> StateT s m () put s = StateT $ \_ -> return ((), s) --- | Monadic state transformer.------      Maps an old state to a new state inside a state monad.---      The old state is thrown away.-+-- | @'modify' f@ is an action that updates the state to the result of+-- applying @f@ to the current state. modify :: (Monad m) => (s -> s) -> StateT s m () modify f = do     s <- get     put (f s) --- | Gets specific component of the state, using a projection function+-- | Get a specific component of the state, using a projection function -- supplied.-+--+-- * @'gets' f = 'liftM' f 'get'@ gets :: (Monad m) => (s -> a) -> StateT s m a gets f = do     s <- get@@ -269,6 +264,30 @@  {- $examples +Parser from ParseLib with Hugs:++> type Parser a = StateT String [] a+>    ==> StateT (String -> [(a,String)])++For example, item can be written as:++> item = do (x:xs) <- get+>        put xs+>        return x+>+> type BoringState s a = StateT s Identity a+>      ==> StateT (s -> Identity (a,s))+>+> type StateWithIO s a = StateT s IO a+>      ==> StateT (s -> IO (a,s))+>+> type StateWithErr s a = StateT s Maybe a+>      ==> StateT (s -> Maybe (a,s))++-}++{- $counting+ A function to increment a counter.  Taken from the paper /Generalising Monads to Arrows/, John Hughes (<http://www.math.chalmers.se/~rjmh/>), November 1998:@@ -288,6 +307,10 @@ > plus :: Int -> Int -> Int > plus n x = execState (sequence $ replicate n tick) x +-}++{- $labelling+ An example from /The Craft of Functional Programming/, Simon Thompson (<http://www.cs.kent.ac.uk/people/staff/sjt/>), Addison-Wesley 1999: \"Given an arbitrary tree, transform it to a@@ -340,4 +363,5 @@ > sumTree :: (Num a) => Tree a -> a > sumTree Nil = 0 > sumTree (Node e t1 t2) = e + (sumTree t1) + (sumTree t2)+ -}
Control/Monad/Trans/Writer/Lazy.hs view
@@ -9,7 +9,15 @@ -- Stability   :  experimental -- Portability :  portable ----- Lazy writer monads.+-- The lazy 'WriterT' monad transformer, which adds collection of+-- outputs (such as a count or string output) to a given monad.+--+-- This version builds its output lazily; for a strict version, see+-- "Control.Monad.Trans.Writer.Strict", which has the same interface.+--+-- This monad transformer provides only limited access to the output+-- during the computation.  For more general access, use+-- "Control.Monad.Trans.State" instead. -----------------------------------------------------------------------------  module Control.Monad.Trans.Writer.Lazy (@@ -26,8 +34,8 @@     -- * Writer operations     tell,     listen,-    pass,     listens,+    pass,     censor,     -- * Lifting other operations     liftCallCC,@@ -44,32 +52,58 @@ import Data.Monoid  -- ------------------------------------------------------------------------------ Our parameterizable writer monad-+-- | A writer monad parameterized by the type @w@ of output to accumulate.+--+-- The 'return' function produces the output 'mempty', while @>>=@+-- combines the outputs of the subcomputations using 'mappend'. type Writer w = WriterT w Identity +-- | Construct a writer computation from a (result, output) pair.+-- (The inverse of 'runWriter'.) writer :: (a, w) -> Writer w a writer = WriterT . Identity +-- | Unwrap a writer computation as a (result, output) pair.+-- (The inverse of 'writer'.) runWriter :: Writer w a -> (a, w) runWriter = runIdentity . runWriterT +-- | Extract the output from a writer computation.+--+-- * @'execWriter' m = 'snd' ('runWriter' m)@ execWriter :: Writer w a -> w execWriter m = snd (runWriter m) +-- | Map both the return value and output of a computation using+-- the given function.+--+-- * @'runWriter' ('mapWriter' f m) = f ('runWriter' m@) mapWriter :: ((a, w) -> (b, w')) -> Writer w a -> Writer w' b mapWriter f = mapWriterT (Identity . f . runIdentity)  -- ------------------------------------------------------------------------------ Our parameterizable writer monad, with an inner monad-+-- | A writer monad parameterized by:+--+--   * @w@ - the output to accumulate.+--+--   * @m@ - The inner monad.+--+-- The 'return' function produces the output 'mempty', while @>>=@+-- combines the outputs of the subcomputations using 'mappend'. newtype WriterT w m a = WriterT { runWriterT :: m (a, w) } +-- | Extract the output from a writer computation.+--+-- * @'execWriterT' m = 'liftM' 'snd' ('runWriterT' m)@ execWriterT :: Monad m => WriterT w m a -> m w execWriterT m = do     ~(_, w) <- runWriterT m     return w +-- | Map both the return value and output of a computation using+-- the given function.+--+-- * @'runWriterT' ('mapWriterT' f m) = f ('runWriterT' m@) mapWriterT :: (m (a, w) -> n (b, w')) -> WriterT w m a -> WriterT w' n b mapWriterT f m = WriterT $ f (runWriterT m) @@ -108,24 +142,47 @@ instance (Monoid w, MonadIO m) => MonadIO (WriterT w m) where     liftIO = lift . liftIO +-- | @'tell' w@ is an action that produces the output @w@. tell :: (Monoid w, Monad m) => w -> WriterT w m () tell w = WriterT $ return ((), w) +-- | @'listen' m@ is an action that executes the action @m@ and adds its+-- output to the value of the computation.+--+-- * @'runWriterT' ('listen' m) = 'liftM' (\\(a, w) -> ((a, w), w)) ('runWriterT' m)@ listen :: (Monoid w, Monad m) => WriterT w m a -> WriterT w m (a, w) listen m = WriterT $ do     ~(a, w) <- runWriterT m     return ((a, w), w) -pass :: (Monoid w, Monad m) => WriterT w m (a, w -> w) -> WriterT w m a-pass m = WriterT $ do-    ~((a, f), w) <- runWriterT m-    return (a, f w)-+-- | @'listens' f m@ is an action that executes the action @m@ and adds+-- the result of applying @f@ to the output to the value of the computation.+--+-- * @'listens' f m = 'liftM' (id *** f) ('listen' m)@+--+-- * @'runWriterT' ('listens' f m) = 'liftM' (\\(a, w) -> ((a, f w), w)) ('runWriterT' m)@ listens :: (Monoid w, Monad m) => (w -> b) -> WriterT w m a -> WriterT w m (a, b) listens f m = do     ~(a, w) <- listen m     return (a, f w) +-- | @'pass' m@ is an action that executes the action @m@, which returns+-- a value and a function, and returns the value, applying the function+-- to the output.+--+-- * @'runWriterT' ('pass' m) = 'liftM' (\\((a, f), w) -> (a, f w)) ('runWriterT' m)@+pass :: (Monoid w, Monad m) => WriterT w m (a, w -> w) -> WriterT w m a+pass m = WriterT $ do+    ~((a, f), w) <- runWriterT m+    return (a, f w)++-- | @'censor' f m@ is an action that executes the action @m@ and+-- applies the function @f@ to its output, leaving the return value+-- unchanged.+--+-- * @'censor' f m = 'pass' ('liftM' (\\x -> (x,f)) m)@+--+-- * @'runWriterT' ('censor' f m) = 'liftM' (\\(a, w) -> (a, f w)) ('runWriterT' m)@ censor :: (Monoid w, Monad m) => (w -> w) -> WriterT w m a -> WriterT w m a censor f m = pass $ do     a <- m
Control/Monad/Trans/Writer/Strict.hs view
@@ -9,7 +9,15 @@ -- Stability   :  experimental -- Portability :  portable ----- Strict writer monads.+-- The strict 'WriterT' monad transformer, which adds collection of+-- outputs (such as a count or string output) to a given monad.+--+-- This version builds its output strictly; for a lazy version, see+-- "Control.Monad.Trans.Writer.Lazy", which has the same interface.+--+-- This monad transformer provides only limited access to the output+-- during the computation.  For more general access, use+-- "Control.Monad.Trans.State" instead. -----------------------------------------------------------------------------  module Control.Monad.Trans.Writer.Strict (@@ -26,8 +34,8 @@     -- * Writer operations     tell,     listen,-    pass,     listens,+    pass,     censor,     -- * Lifting other operations     liftCallCC,@@ -44,32 +52,58 @@ import Data.Monoid  -- ------------------------------------------------------------------------------ Our parameterizable writer monad-+-- | A writer monad parameterized by the type @w@ of output to accumulate.+--+-- The 'return' function produces the output 'mempty', while @>>=@+-- combines the outputs of the subcomputations using 'mappend'. type Writer w = WriterT w Identity +-- | Construct a writer computation from a (result, output) pair.+-- (The inverse of 'runWriter'.) writer :: (a, w) -> Writer w a writer = WriterT . Identity +-- | Unwrap a writer computation as a (result, output) pair.+-- (The inverse of 'writer'.) runWriter :: Writer w a -> (a, w) runWriter = runIdentity . runWriterT +-- | Extract the output from a writer computation.+--+-- * @'execWriter' m = 'snd' ('runWriter' m)@ execWriter :: Writer w a -> w execWriter m = snd (runWriter m) +-- | Map both the return value and output of a computation using+-- the given function.+--+-- * @'runWriter' ('mapWriter' f m) = f ('runWriter' m@) mapWriter :: ((a, w) -> (b, w')) -> Writer w a -> Writer w' b mapWriter f = mapWriterT (Identity . f . runIdentity)  -- ------------------------------------------------------------------------------ Our parameterizable writer monad, with an inner monad-+-- | A writer monad parameterized by:+--+--   * @w@ - the output to accumulate.+--+--   * @m@ - The inner monad.+--+-- The 'return' function produces the output 'mempty', while @>>=@+-- combines the outputs of the subcomputations using 'mappend'. newtype WriterT w m a = WriterT { runWriterT :: m (a, w) } +-- | Extract the output from a writer computation.+--+-- * @'execWriterT' m = 'liftM' 'snd' ('runWriterT' m)@ execWriterT :: Monad m => WriterT w m a -> m w execWriterT m = do     (_, w) <- runWriterT m     return w +-- | Map both the return value and output of a computation using+-- the given function.+--+-- * @'runWriterT' ('mapWriterT' f m) = f ('runWriterT' m@) mapWriterT :: (m (a, w) -> n (b, w')) -> WriterT w m a -> WriterT w' n b mapWriterT f m = WriterT $ f (runWriterT m) @@ -108,24 +142,47 @@ instance (Monoid w, MonadIO m) => MonadIO (WriterT w m) where     liftIO = lift . liftIO +-- | @'tell' w@ is an action that produces the output @w@. tell :: (Monoid w, Monad m) => w -> WriterT w m () tell w = WriterT $ return ((), w) +-- | @'listen' m@ is an action that executes the action @m@ and adds its+-- output to the value of the computation.+--+-- * @'runWriterT' ('listen' m) = 'liftM' (\\(a, w) -> ((a, w), w)) ('runWriterT' m)@ listen :: (Monoid w, Monad m) => WriterT w m a -> WriterT w m (a, w) listen m = WriterT $ do     (a, w) <- runWriterT m     return ((a, w), w) -pass :: (Monoid w, Monad m) => WriterT w m (a, w -> w) -> WriterT w m a-pass m = WriterT $ do-    ((a, f), w) <- runWriterT m-    return (a, f w)-+-- | @'listens' f m@ is an action that executes the action @m@ and adds+-- the result of applying @f@ to the output to the value of the computation.+--+-- * @'listens' f m = 'liftM' (id *** f) ('listen' m)@+--+-- * @'runWriterT' ('listens' f m) = 'liftM' (\\(a, w) -> ((a, f w), w)) ('runWriterT' m)@ listens :: (Monoid w, Monad m) => (w -> b) -> WriterT w m a -> WriterT w m (a, b) listens f m = do     (a, w) <- listen m     return (a, f w) +-- | @'pass' m@ is an action that executes the action @m@, which returns+-- a value and a function, and returns the value, applying the function+-- to the output.+--+-- * @'runWriterT' ('pass' m) = 'liftM' (\\((a, f), w) -> (a, f w)) ('runWriterT' m)@+pass :: (Monoid w, Monad m) => WriterT w m (a, w -> w) -> WriterT w m a+pass m = WriterT $ do+    ((a, f), w) <- runWriterT m+    return (a, f w)++-- | @'censor' f m@ is an action that executes the action @m@ and+-- applies the function @f@ to its output, leaving the return value+-- unchanged.+--+-- * @'censor' f m = 'pass' ('liftM' (\\x -> (x,f)) m)@+--+-- * @'runWriterT' ('censor' f m) = 'liftM' (\\(a, w) -> (a, f w)) ('runWriterT' m)@ censor :: (Monoid w, Monad m) => (w -> w) -> WriterT w m a -> WriterT w m a censor f m = pass $ do     a <- m
Data/Functor/Compose.hs view
@@ -18,6 +18,8 @@ import Data.Traversable (Traversable(traverse))  -- | Right-to-left composition of functors.+-- The composition of applicative functors is always applicative,+-- but the composition of monads is not always a monad. newtype Compose f g a = Compose { getCompose :: f (g a) }  instance (Functor f, Functor g) => Functor (Compose f g) where@@ -32,3 +34,7 @@ instance (Applicative f, Applicative g) => Applicative (Compose f g) where     pure x = Compose (pure (pure x))     Compose f <*> Compose x = Compose ((<*>) <$> f <*> x)++instance (Alternative f, Applicative g) => Alternative (Compose f g) where+    empty = Compose empty+    Compose x <|> Compose y = Compose (x <|> y)
+ Data/Functor/Product.hs view
@@ -0,0 +1,39 @@+-- |+-- Module      :  Data.Functor.Product+-- Copyright   :  (c) Ross Paterson 2010+-- License     :  BSD-style (see the file libraries/base/LICENSE)+--+-- Maintainer  :  libraries@haskell.org+-- Stability   :  experimental+-- Portability :  portable+--+-- Products, lifted to functors.++module Data.Functor.Product (+    Product(..),+   ) where++import Control.Applicative+import Data.Foldable (Foldable(foldMap))+import Data.Monoid (mappend)+import Data.Traversable (Traversable(traverse))++-- | Lifted product of functors.+data Product f g a = Pair (f a) (g a)++instance (Functor f, Functor g) => Functor (Product f g) where+    fmap f (Pair x y) = Pair (fmap f x) (fmap f y)++instance (Foldable f, Foldable g) => Foldable (Product f g) where+    foldMap f (Pair x y) = foldMap f x `mappend` foldMap f y++instance (Traversable f, Traversable g) => Traversable (Product f g) where+    traverse f (Pair x y) = Pair <$> traverse f x <*> traverse f y++instance (Applicative f, Applicative g) => Applicative (Product f g) where+    pure x = Pair (pure x) (pure x)+    Pair f g <*> Pair x y = Pair (f <*> x) (g <*> y)++instance (Alternative f, Alternative g) => Alternative (Product f g) where+    empty = Pair empty empty+    Pair x1 y1 <|> Pair x2 y2 = Pair (x1 <|> x2) (y1 <|> y2)
transformers.cabal view
@@ -1,5 +1,5 @@ name:         transformers-version:      0.2.0.0+version:      0.2.1.0 license:      BSD3 license-file: LICENSE author:       Andy Gill, Ross Paterson@@ -50,3 +50,4 @@     Data.Functor.Compose     Data.Functor.Constant     Data.Functor.Identity+    Data.Functor.Product