
Hi all, I'm trying to create a "HasToList" type class. It starts off really simple: class HasToList collection where toList ∷ collection element → [element] instance HasToList Set where toList = Data.Set.toList Unfortunately, this breaks down with Data.EnumSet.EnumSet. So instance HasToList EnumSet where toList = Data.EnumSet.toList doesn't compile and I could not find a way to add "Enum a =>" to either the instance or "toList". (Well, not without making the compiler upset.) With the aid of ConstraintKinds and TypeFamilies (and not much understanding on my end, obviously) I created class HasToList collection where type Requirement collection element :: Constraint toList ∷ Requirement collection element => collection element → [element] instance HasToList Set where type Requirement Set a = () toList = Data.Set.toList instance HasToList EnumSet where type Requirement EnumSet a = Enum a toList = Data.EnumSet.toList This works but now I have to add the constraint to every instance even though only a tiny minority actually need it. Is there a way to add a default "type implementation"? I tried the obvious type Requirement collection element :: Constraint = () and type Requirement collection element :: Constraint type Requirement collection element :: Constraint = () but neither compiles. Another problem is that the compiler can't compile something like this: isteps ∷ HasToList collection ⇒ collection String → [(Int, String)] isteps steps = Data.List.Index.indexed (toList steps) because it doesn't know which constraint to apply ("Could not deduce: Requirement hasToList String"). That seems fair but also irrelevant at this point. I feel like this is all far too complicated for what I'm trying to accomplish. :-) While I would like to have an answer to the questions above, I guess what I really want is a simpler way to implement HasToList. Cheers, Hilco