Java-like

Ben Rudiak-Gould Benjamin.Rudiak-Gould at cl.cam.ac.uk
Wed Feb 8 10:25:49 EST 2006


Bulat Ziganshin wrote:
>>> main = do return "xx" >>= ((\x -> print x) :: Show a => a -> IO ())
>>> main2 = do return "xx" >>= (\(x:: (forall a . (Show a) => a)) -> print x)
>>> main3 = do (x :: forall a . Show a => a) <- return "xx"
>>>            print x
> 
> the second and third variant should do the same, to my mind.

Well, you need to change your mind. :-) Forall is like a function; when you 
write

     forall a. Show a => a -> IO ()

it means something like

     (a::Type) -> ShowDict a -> a -> IO ()

In other words, the caller supplies three things: the type a, a dictionary 
for Show a, and a value of a. But when you write

     forall a. Show a => a

it means something like

     (a::Type) -> ShowDict a -> a

In other words, the caller supplies two things, the type a and a dictionary 
for Show a, and the callee *returns* a value of a. In this case the callee 
has to be prepared to produce a value of whatever type the caller requests, 
and it can't do that if it only has a String.

On the other hand

     exists a. Show a && a

means

     (a::Type, ShowDict a, a)

i.e. the callee chooses the type and dictionary as well as the value, which 
is what you need here.

-- Ben



More information about the Haskell-prime mailing list