Adding an ignore function to Control.Monad

Henning Thielemann lemming at henning-thielemann.de
Fri Aug 14 13:29:52 EDT 2009


On Thu, 11 Jun 2009, John Meacham wrote:

> On Thu, Jun 11, 2009 at 11:21:54PM +0100, Sittampalam, Ganesh wrote:
>>
>> On the flip side, could you give some examples where ignoring return
>> values is useful and natural?
>
> certainly, the very useful parser example mentioned.
>
> (char 'x' >> char 'y') - we want to parse x, then y

Are you really interested to only ignore the result of the first 'char' 
parser and maintain the result of the second one?

> (char 'x' `mplus` char 'y') - we want to parse one of x or y, returning
> which one we got so we can change behavior based on it.

Indeed using the same 'char' parser in both cases is convenient. It seems 
that parser monads are different from IO monad, in that it is more common 
to ignore results. (Or parser monads are developed with the simplicity of 
ignoring results in mind.)



With
  char :: Char -> Parser Char

  ignore :: Functor m => m a -> m Ignore  (or m ())
  ignore = fmap (const Ignore)

we would have to write
  ignore (char 'x') >> char 'y'
  char 'x' `mplus` char 'y'

With
  char :: Char -> Parser Ignore  (or Parser ())

  echo :: Functor m => (a -> m Ignore) -> (a -> m a)
  echo f x = fmap (const x) $ f x

we would write
  char 'x' >> char 'y'
  echo char 'x' `mplus` echo char 'y'


If the parser library anticipates frequent use of ignore it could define a 
type class.

class IgnorableChar a where
    wrapChar :: Char -> a

class IgnorableChar Ignore where
    wrapChar _ = Ignore

class IgnorableChar Char where
    wrapChar = id

char :: IgnorableChar char => Char -> Parser char


Cumbersome to define, but as simple to use as today's 'char' with today's 
'>>'. Just as a compromise for parser libraries.

Ok, all these suggestions make things more complicated. Convenience vs. 
safety - It's certainly a matter of taste which one is more important for 
you.


> When using the 'Writer' monad or similar it comes up a whole lot.
> sometimes you are interested in the result, sometimes the written value,
> sometimes both.

I think one should use Monoid class directly whereever possible. I have 
seen frequently that people use Writer monad instead of Monoid only 
because of the do notation.


More information about the Libraries mailing list