
Hi Brent,
Think about what (show . host $ a) does. It takes 'a', converts it to... any type which is an instance of IPHost, and then shows that, turning it into a String. But there can be multiple types which are instances of IPHost, and each of them could have a *different* Show instance. So the exact String you get out depends on what type you pick... but there's no way for Haskell to infer which type to use. This is why it suggests to add a type signature. But I think there is probably some confusion that needs to be cleared up, the code you have doesn't quite make sense. Here are some questions to ask yourself:
1. Do you really want to be able to have multiple instances for IPHost and IPMask? (The answer might legitimately be 'yes', I'm just making sure.) What sorts of types do you have in mind that will be instances of these classes?
Yes. Basically my goal was to have something like: data IPv4Host = IPv4Host Word32 deriving (Show) instance IPHost IPv4Host where data IPv4Mask = IPv4Mask Word32 deriving (Show) instance IPMask IPv4Mask where data IPv4Addr = IPv4Addr IPv4Host IPv4Mask instance IPAddr IPv4Addr where and the equivalent for IPv6 (to be implemented later when I fugre out how to do it...)
2. Do you really intend for the 'host' and 'mask' methods of the IPAddr class to be able to return *any* types which are instances of IPHost and IPMask, respectively? (This is what the code says right now.) This is actually impossible given that IPHost and IPMask have no methods. Or do you mean that for a given instance of IPAddr, the 'host' method (say) will return some *particular* type which happens to be an instance of IPHost, but which type is returned may differ between instances of IPAddr?
Yes! That's exactly what I want (and yes there will be methods eventually in those classes)
If that's really what you mean, I would suggest either using a multi-parameter type class, like so:
class (IPHost h, IPMask m) => IPAddr a h m where host :: a -> h mask :: a -> m
Ok... So I guess the instance declaration for IPv4Addr will then become this: instance IPAddr IPv4Addr IPv4Host IPv4Mask where but how do I adjust the showIPAddr function to deal with that? I tried this: showIPAddr :: (IPAddr a h m) => a -> String but something is still missing, I get: Could not deduce (IPAddr a b m) from the context (IPAddr a h1 m1) arising from a use of `host' at IP.hs:23:23-26 Possible fix: add (IPAddr a b m) to the context of the type signature for `showIPAddr' In the second argument of `(.)', namely `host' In the first argument of `($)', namely `show . host' In the first argument of `(++)', namely `(show . host $ a)' Thanks a lot, Patrick
OR using existential quantification to hide the particular types returned by 'host' and 'mask'.
-Brent _______________________________________________ Beginners mailing list Beginners@haskell.org http://www.haskell.org/mailman/listinfo/beginners
-- ===================== Patrick LeBoutillier Rosemère, Québec, Canada