This cannot be done. The reason is that the function can use its argument of type
a to determine what
IO action is executed. Consider
action :: Bool -> IO String
action True = putStrLn "Enter something:" >> getLine
action False = exitFailure
Now if you'd convert it somehow to
IO (Bool -> String) and evaluate this action, what should happen? There is no solution. We cannot decide if we should read a string or exit, because we don't know the
Bool argument yet (and we may never know it, if the resulting function isn't called on an argument).
John's answer is a bad idea. It simply lets the IO action escape into pure computations, which will make your life miserable and you'll lose Haskell's referential transparency! For example running:
main = unsafe action >> return ()
will do nothing even though the IO action was called. Moreover, if we modify it a bit:
main = do
f <- unsafe action
putStrLn "The action has been called, calling its pure output function."
putStrLn $ "The result is: " ++ f True
you'll see that the
action that asks for an input is executed in a pure computation, inside calling
f. You'll have no guarantee when (if at all) the action is executed!
Edit: As others pointed out, it isn't specific just to
IO. For example, if the monad were
Maybe, you couldn't implement
(a -> Maybe b) -> Maybe (a -> b). Or for
Either, you couldn't implement
(a -> Either c b) -> Either c (a -> b). The key is always that for
a -> m b we can choose different effects depending on
a, while in
m (a -> b) the effect must be fixed.