3
replicate 3 "hi"

produces

["hi", "hi", "hi"]

but

liftM (replicate 3) "hi"

produces

["hhh", "iii"]

How the liftM operates (precisely)?

Cartesius00
  • 23,584
  • 43
  • 124
  • 195

2 Answers2

7

The liftM function is another name for fmap*, which is equivalent to map when it operates on lists.

liftM (replicate 3) "hi"
  = [replicate 3 x | x <- "hi"]
  = [replicate 3 'h', replicate 3 'i']
  = ["hhh", "iii"]

Footnotes

* The difference between liftM and fmap is the different class context, since due to historical reasons, Monad does not imply Functor.

Dietrich Epp
  • 205,541
  • 37
  • 345
  • 415
6

Summary: liftM = map.


The liftM function has type Monad m => (a -> b) -> m a -> m b. That is, it takes a function and something in a monad and applies the function "through" the monad. (Or, to look at it another way, it has type Monad m => (a -> b) -> (m a -> m b), i.e. it converts a function into one that operates through a monad.)

In this case we have liftM (replicate 3) ['h','i'] (remember that "hi" is just shorthand for a list of the individual characters), so the monad in question is the list monad. The definition of liftM for lists is equivalent to map (the two functions have the same type, which is a big hint.) Thus:

liftM (replicate 3) ['h','i'] = map (replicate 3) ['h','i']
     = [replicate 3 'h', replicate 3 'i'] = ["hhh","iii"]
huon
  • 94,605
  • 21
  • 231
  • 225