module Singletons.Classes where import Prelude hiding (const) import Singletons.Nat import Data.Singletons import Data.Singletons.TH import Language.Haskell.TH.Desugar import Data.Singletons.Prelude.Ord import Data.Singletons.Prelude.Eq $(singletons [d| const :: a -> b -> a const x _ = x class MyOrd a where mycompare :: a -> a -> Ordering (<=>) :: a -> a -> Ordering (<=>) = mycompare infix 4 <=> instance MyOrd Nat where Zero `mycompare` Zero = EQ Zero `mycompare` (Succ _) = LT (Succ _) `mycompare` Zero = GT (Succ n) `mycompare` (Succ m) = m `mycompare` n -- test eta-expansion instance MyOrd () where mycompare _ = const EQ data Foo = A | B fooCompare :: Foo -> Foo -> Ordering fooCompare A A = EQ fooCompare A B = LT fooCompare B B = GT fooCompare B A = EQ instance MyOrd Foo where -- test that values in instance definitions are eta-expanded mycompare = fooCompare data Foo2 = F | G instance Eq Foo2 where F == F = True G == G = True F == G = False G == F = False |]) $(promote [d| -- instance with overlaping equations. Tests #56 instance MyOrd Foo2 where F `mycompare` F = EQ F `mycompare` _ = LT _ `mycompare` _ = GT instance Ord Foo2 where F `compare` F = EQ F `compare` _ = LT _ `compare` _ = GT |]) -- check promotion across different splices (#55) $(singletons [d| data Nat' = Zero' | Succ' Nat' instance MyOrd Nat' where Zero' `mycompare` Zero' = EQ Zero' `mycompare` (Succ' _) = LT (Succ' _) `mycompare` Zero' = GT (Succ' n) `mycompare` (Succ' m) = m `mycompare` n |]) foo1a :: Proxy (Zero `Mycompare` (Succ Zero)) foo1a = Proxy foo1b :: Proxy LT foo1b = foo1a foo2a :: Proxy (A `Mycompare` A) foo2a = Proxy foo2b :: Proxy EQ foo2b = foo2a foo3a :: Proxy ('() `Mycompare` '()) foo3a = Proxy foo3b :: Proxy EQ foo3b = foo3a foo4a :: Proxy (Succ' Zero' <=> Zero') foo4a = Proxy foo4b :: Proxy GT foo4b = foo4a