{-# LANGUAGE GADTs #-} -- From the ghc-users mailing list module Foo where data TValue t where TList :: [a] -> TValue [a] instance (Eq b) => Eq (TValue b) where (==) (TList p) (TList q) = (==) p q {- My reply to the list Here's the reasoning (I have done a bit of renaming). * The TList constructor really has type TList :: forall a. forall x. (a~[x]) => [x] -> TValue a * So in the pattern match we have (Eq b) available from the instance header TList p :: TValue b x is a skolem, existentially bound by the pattern p :: [x] b ~ [x] available from the pattern match * On the RHS we find we need (Eq [x]). * So the constraint problem we have is (Eq b, b~[x]) => Eq [x] ["Given" => "Wanted"] Can we prove this? From the two given constraints we can see that we also have Eq [x], and that certainly proves Eq [x]. Nevertheless, it's a bit delicate. If we didn't notice all the consequences of the "given" constraints, we might use the top-level Eq a => Eq [a] instance to solve the wanted Eq [x]. And now we need Eq x, which *isn't* a consequence of (Eq b, b~[x]). -}