samedi 24 janvier 2015

Using Haskell type classes to enforce commutativity


I want to define a type class for geometric objects that can be intersected together:



class Intersect a b c | a b -> c where
intersect :: a -> b -> c
-- Language extensions: -XMultiParamTypeClasses, -XFunctionalDependencies


The idea is to have a general-purpose intersection functions that can handle objects of different types. One could imagine such instances as



instance Intersect Line Plane (Maybe Point) where
...
instance Intersect Plane Plane (Maybe Line) where
...


But I also want to declare that intersection is commutative:



instance (Intersect a b c) => Intersect b a c where
intersect x y = intersect y x
-- Language extensions: -XUndecidableInstances


The problem is that whenever I evaluate intersect x y without first defining an instance of the form Intersect a b c, where a is the type of x and b is the type of y, the program goes into an infinite loop, presumably caused by recursive instance declaration about commutativity. Ideally I want something like intersect Egg Bacon to fail to type-check because no such instance was defined, not trap me in an infinite loop. How can I implement this?





Aucun commentaire:

Enregistrer un commentaire