I have defined a type X
as
newtype X i o = X { runX :: Int -> i -> IO o }
I have made an instance of Functor
, Applicative
and Monad
with
instance Functor (X i) where
fmap f a = X $ \ i o -> liftA f $ runX a i o
instance Applicative (X i) where
pure x = X $ \ _ _ -> return x
a <*> b = X $ \ i o -> liftA2 (<*>) (runX a i o) (runX b i o)
instance Monad (X i) where
return = pure
a >> b = X $ \ i o -> runX a i o >> runX b i o
As you could probably tell, I have been, thusfar, unable to come up with a definition for >>=
, and so have excluded it. I expected this to error on compile, but in fact, all it did was raise a warning. Fine, so it doesn't check that all the methods of a class are defined, but then surely I can't actually use >>=
. Nope, wrong once again. To my great astonishment, GHCi happily evaluates let x = pure 5 >>= pure
. Control.Monad
does not export a default definition of >>=
, and I certainly haven't defined one, so how is this possible?
Critical reading also means that you are able to distinguish the information that is clear stated. EXPLICIT in the text from ideas that are suggested. IMPLICIT this is will help you make inferences about what your read.
Given your corrected definition, if I try to define and then use x
, I get the expected runtime exception:
λ> let x = pure 5 >>= pure :: X Int Int
λ> runX x 5 5
*** Exception: foo.hs:12:10-20: No instance nor default method for class operation GHC.Base.>>=
There are two possible reasons why you would not see that.
The first is that you just ran the let
but never tried evaluating the result. Since Haskell is lazy, let x = ...
doesn't actually do anything. x
will only get evaluated when you actually try to use it (with, ie, runX
), so that's when you would hit the error.
The other possibility is that you used a let
without specifying the type:
λ> let x = pure 5 >>= pure
λ> x
5
Here, x
is polymorphic in the monad m
it uses. To print something useful for polymorphic terms like this one, ghci defaults m
to IO
, which works correctly and gives you 5
, but doesn't tell you anything useful about your custom monad.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With