Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Maybe monad bind function precedence

In this tutorial I've found the following snippet:

deposit :: (Num a) => a -> a -> Maybe a
deposit value account = Just (account + value)

withdraw :: (Num a,Ord a) => a -> a -> Maybe a
withdraw value account = if (account < value) 
                         then Nothing 
                         else Just (account - value)

eligible :: (Num a, Ord a) => a -> Maybe Bool
eligible account =
  deposit 100 account >>=
  withdraw 200 >>=
  deposit 100  >>=
  withdraw 300 >>=
  deposit 1000 >>
  return True

main = do
  print $ eligible 300 -- Just True
  print $ eligible 299 -- Nothing

I can't figure out how the >>= function is supposed to work. At first it takes a Maybe a value as its first parameter: deposit 100 account >>=

Afterwards, however it seems to take a -> Maybe a as its first parameter: withdraw 200 >>= How could this be approved by the compiler? Shouldn't >>= always take Maybe a as its first parameter?

A possible solution would be if the >>= function's precedence would work in the following way: ((a >>= b) >>= c) >>= d

But as far as I know, it is the opposite: a >>= (b >>= (c >>= d))

like image 914
Attila Kun Avatar asked Jul 03 '12 14:07

Attila Kun


People also ask

Is maybe a monad?

The Maybe sum type is a useful data type that forms a functor. Like many other useful functors, it also forms a monad.

What is monadic bind?

Monadic bind is the name given to the (>>=) function or bind function, also known as chain, flatMap, or joinMap. I personally like to call it the “then” function borrowing the word from JavaScript Promises. It is much more intuitive that way if you read it as “then” instead of “bind”.

Is maybe a monad in Haskell?

The Maybe type is also a monad. It is a simple kind of error monad, where all errors are represented by Nothing . A richer error monad can be built using the Either type.

What is an example of a monad?

For example, in the IO monad, x >>= y performs two actions sequentially, passing the result of the first into the second. For the other built-in monads, lists and the Maybe type, these monadic operations can be understood in terms of passing zero or more values from one calculation to the next.


1 Answers

as far as I know, it is the opposite: a >>= (b >>= (c >>= d))

nope.

GHCi> :i >>=
class Monad m where
  (>>=) :: m a -> (a -> m b) -> m b
  ...
    -- Defined in `GHC.Base'
infixl 1 >>=

infixl means that it's left-associative, so a >>= b >>= c >>= d ≡ ((a >>= b) >>= c) >>= d.

It wouldn't actually make much sense if it were infixr, would it? >>= always returns a monad, and its RHS takes a function. So in any chain of monadic expressions linked with >>= would be in the (->) r monad, which is hardly the most useful one.

like image 77
leftaroundabout Avatar answered Sep 18 '22 01:09

leftaroundabout