{- From: Kevin Hammond To: partain Subject: Nasty Overloading Date: Wed, 23 Oct 91 16:19:46 BST -} module Main where class Foo a where o1 :: a -> a -> Bool o2 :: a -> Int -- o2 :: Int -- Lennart: The type of method o2 does not contain the variable a -- (and it must according to line 1 page 29 of the manual). class Foo tyvar => Bar tyvar where o3 :: a -> tyvar -> tyvar -- class (Eq a, Foo a) => Baz a where class (Ord a, Foo a) => Baz a where o4 :: a -> a -> (String,String,String,a) instance (Ord a, Foo a) => Foo [a] where o2 x = 100 o1 a b = a < b || o1 (head a) (head b) -- instance Bar [a] where instance (Ord a, Foo a) => Bar [a] where o3 x l = [] -- -- Lennart: I guess the instance declaration -- instance Bar [w] where -- o3 x l = [] -- is wrong because to be a Bar you have to be a Foo. For [w] to -- be a Foo, w has to be Ord and Foo. But w is not Ord or Foo in -- this instance declaration so it must be wrong. (Page 31, line -- 7: The context c' must imply ...) instance Baz a => Baz [a] where o4 [] [] = ("Nil", "Nil", "Nil", []) o4 l1 l2 = (if o1 l1 l2 then "Y" else "N", if l1 == l2 then "Y" else "N", -- if o4 (head l1) (head l2) then "Y" else "N", case o4 (head l1) (head l2) of (_,_,_,l3) -> if (o1 (head l1) l3) then "Y" else "N", l1 ++ l2 ) instance Foo Int where o2 x = x o1 i j = i == j instance Bar Int where o3 _ j = j + 1 instance Baz Int where -- o4 i j = i > j o4 i j = (if i>j then "Y" else "Z", "p", "q", i+j) --simpl:o4 i j = ("Z", "p", "q", i+j) {- also works w/ glhc! -} main = if o4 [1,2,3] [1,3,2::Int] /= ("Y","N","Y",[1,2,3,1,3,2]) then (print "43\n") else (print "144\n") {- works: glhc main = case o4 [1,2,3] [1,3,2::Int] of (s1,s2,s3,x) -> print s1 main = case o4 ([]::[Int]) ([]::[Int]) of (s1,s2,s3,x) -> print s1 -} {- simple main: breaks nhc, works w/ glhc main = case o4 (3::Int) (4::Int) of (s1,s2,s3,x) -> print s1 -}