coming from the Ocaml community, I'm trying to learn a bit of Haskell. The transition goes quite well but I'm a bit confused with debugging. I used to put (lots of) "printf" in my ocaml code, to inspect some intermediate values, or as flag to see where the computation exactly failed.
Since printf is an IO action, do I have to lift all my haskell code inside the IO monad to be able to this kind of debugging ? Or is there a better way to do this (I really don't want to do it by hand if it can be avoided)
I also find the trace function : http://www.haskell.org/haskellwiki/Debugging#Printf_and_friends which seems exactly what I want, but I don't understand it's type: there is no IO anywhere! Can someone explain me the behaviour of the trace function ?
trace
is the easiest to use method for debugging. It's not in IO
exactly for the reason you pointed: no need to lift your code in the IO
monad. It's implemented like this
trace :: String -> a -> a
trace string expr = unsafePerformIO $ do
putTraceMsg string
return expr
So there is IO behind the scenes but unsafePerformIO
is used to escape out of it. That's a function which potentially breaks referential transparency which you can guess looking at its type IO a -> a
and also its name.