[Haskell-cafe] Re: Parsers are monadic?

Claus Reinke claus.reinke at talk21.com
Mon Jul 2 09:54:43 EDT 2007


>  class Monad m => MonadError e m | m -> e where
>    throwError :: e -> m a
>    catchError :: m a -> (e -> m a) -> m a
>..
> power of TwoCont? I mean, it still seems like there's an operation
> missing that supplies new left and right continuations at once.

i guess, instead of one DiMonad with two sets of operations,  i'd 
prefer to have two separate Monads with the ability to connect 
them, so that failure in one is success in the other, but i guess we 
need some way to tell which is which.

using MonadError to handle error continuations on top of a Monad
to handle success continuation is a lot like using a MonadReader to
hold error continuations on top of the base Monad. consider

    class (Monad m) => MonadReader r m | m -> r where
      ask :: m r
      local :: (r -> r) -> m a -> m a

where  r = e -> m a. then

    throwError = \e->ask >>= \h->h e
    catchError m h = local (const h) m

in other words, supplying both continuations is straightforward,
although syntactic sugar only supports supplying one, in line with 
the bias towards one of the two continuations:

    m `doubleBind` (s,f) = m `catchError` f >>= s 

i find myself doing something like this frequently, whenever i use 
constructs like

     m >>= \x-> a x `mplus` b x
    m >>= maybe a b
    m >>= either a b

btw, it might be useful if throwing an error would reverse the roles of 
the two continuations, instead of throwing away the success continuation.

then the error handler itself could either return (abandoning the original
success continuation) or throw (resuming the original  continuation).
that would interfere with the use of throw to pass on unhandled errors,
but then we could be more specific about which direction to throw.

claus



More information about the Haskell-Cafe mailing list