{-# LANGUAGE MultiParamTypeClasses, FunctionalDependencies, FlexibleInstances, UndecidableInstances, RankNTypes, FlexibleContexts, LambdaCase, ScopedTypeVariables, Safe #-}
module Data.Chatty.Hetero where
infixr 9 :-:
data Cons a b = (:-:) a b
data Nil = Nil
class Append a b ab | a b -> ab where
tappend :: a -> b -> ab
instance Append Nil b b where
tappend :: Nil -> b -> b
tappend Nil
Nil b
b = b
b
instance Append b c bc => Append (Cons a b) c (Cons a bc) where
tappend :: Cons a b -> c -> Cons a bc
tappend (a
a :-: b
b) c
c = a
a a -> bc -> Cons a bc
forall a b. a -> b -> Cons a b
:-: b -> c -> bc
forall a b ab. Append a b ab => a -> b -> ab
tappend b
b c
c
class IntoMaybe a ar | a -> ar where
tjust :: a -> ar
tnothing :: a -> ar
instance IntoMaybe Nil Nil where
tjust :: Nil -> Nil
tjust Nil
Nil = Nil
Nil
tnothing :: Nil -> Nil
tnothing Nil
a = Nil
Nil
instance IntoMaybe (Cons a as) (Cons (Maybe (Cons a as)) Nil) where
tjust :: Cons a as -> Cons (Maybe (Cons a as)) Nil
tjust Cons a as
a = Cons a as -> Maybe (Cons a as)
forall a. a -> Maybe a
Just Cons a as
a Maybe (Cons a as) -> Nil -> Cons (Maybe (Cons a as)) Nil
forall a b. a -> b -> Cons a b
:-: Nil
Nil
tnothing :: Cons a as -> Cons (Maybe (Cons a as)) Nil
tnothing Cons a as
a = Maybe (Cons a as)
forall a. Maybe a
Nothing Maybe (Cons a as) -> Nil -> Cons (Maybe (Cons a as)) Nil
forall a b. a -> b -> Cons a b
:-: Nil
Nil
class Tuplify l t | l -> t where
tuplify :: l -> t
instance Tuplify Nil () where
tuplify :: Nil -> ()
tuplify Nil
Nil = ()
instance Tuplify a ar => Tuplify (Cons a Nil) ar where
tuplify :: Cons a Nil -> ar
tuplify (a
a :-: Nil
Nil) = a -> ar
forall l t. Tuplify l t => l -> t
tuplify a
a
instance (Tuplify a ar, Tuplify b br) => Tuplify (Cons a (Cons b Nil)) (ar,br) where
tuplify :: Cons a (Cons b Nil) -> (ar, br)
tuplify (a
a :-: b
b :-: Nil
Nil) = (a -> ar
forall l t. Tuplify l t => l -> t
tuplify a
a, b -> br
forall l t. Tuplify l t => l -> t
tuplify b
b)
instance (Tuplify a ar, Tuplify b br, Tuplify c cr) => Tuplify (Cons a (Cons b (Cons c Nil))) (ar,br,cr) where
tuplify :: Cons a (Cons b (Cons c Nil)) -> (ar, br, cr)
tuplify (a
a :-: b
b :-: c
c :-: Nil
Nil) = (a -> ar
forall l t. Tuplify l t => l -> t
tuplify a
a, b -> br
forall l t. Tuplify l t => l -> t
tuplify b
b, c -> cr
forall l t. Tuplify l t => l -> t
tuplify c
c)
instance (Tuplify a ar, Tuplify b br, Tuplify c cr, Tuplify d dr) => Tuplify (Cons a (Cons b (Cons c (Cons d Nil)))) (ar,br,cr,dr) where
tuplify :: Cons a (Cons b (Cons c (Cons d Nil))) -> (ar, br, cr, dr)
tuplify (a
a :-: b
b :-: c
c :-: d
d :-: Nil
Nil) = (a -> ar
forall l t. Tuplify l t => l -> t
tuplify a
a, b -> br
forall l t. Tuplify l t => l -> t
tuplify b
b,c -> cr
forall l t. Tuplify l t => l -> t
tuplify c
c,d -> dr
forall l t. Tuplify l t => l -> t
tuplify d
d)
instance (Tuplify a ar, Tuplify b br, Tuplify c cr, Tuplify d dr, Tuplify e er) => Tuplify (Cons a (Cons b (Cons c (Cons d (Cons e Nil))))) (ar,br,cr,dr,er) where
tuplify :: Cons a (Cons b (Cons c (Cons d (Cons e Nil))))
-> (ar, br, cr, dr, er)
tuplify (a
a :-: b
b :-: c
c :-: d
d :-: e
e :-: Nil
Nil) = (a -> ar
forall l t. Tuplify l t => l -> t
tuplify a
a,b -> br
forall l t. Tuplify l t => l -> t
tuplify b
b,c -> cr
forall l t. Tuplify l t => l -> t
tuplify c
c,d -> dr
forall l t. Tuplify l t => l -> t
tuplify d
d,e -> er
forall l t. Tuplify l t => l -> t
tuplify e
e)
instance (Tuplify a ar, Tuplify b br, Tuplify c cr, Tuplify d dr, Tuplify e er, Tuplify f fr) => Tuplify (Cons a (Cons b (Cons c (Cons d (Cons e (Cons f Nil)))))) (ar,br,cr,dr,er,fr) where
tuplify :: Cons a (Cons b (Cons c (Cons d (Cons e (Cons f Nil)))))
-> (ar, br, cr, dr, er, fr)
tuplify (a
a :-: b
b :-: c
c :-: d
d :-: e
e :-: f
f :-: Nil
Nil) = (a -> ar
forall l t. Tuplify l t => l -> t
tuplify a
a,b -> br
forall l t. Tuplify l t => l -> t
tuplify b
b,c -> cr
forall l t. Tuplify l t => l -> t
tuplify c
c,d -> dr
forall l t. Tuplify l t => l -> t
tuplify d
d,e -> er
forall l t. Tuplify l t => l -> t
tuplify e
e,f -> fr
forall l t. Tuplify l t => l -> t
tuplify f
f)
instance Tuplify Int Int where
tuplify :: Int -> Int
tuplify = Int -> Int
forall a. a -> a
id
instance Tuplify Char Char where
tuplify :: Char -> Char
tuplify = Char -> Char
forall a. a -> a
id
instance Tuplify a ar => Tuplify [a] [ar] where
tuplify :: [a] -> [ar]
tuplify = (a -> ar) -> [a] -> [ar]
forall a b. (a -> b) -> [a] -> [b]
map a -> ar
forall l t. Tuplify l t => l -> t
tuplify
instance Tuplify a ar => Tuplify (Maybe a) (Maybe ar) where
tuplify :: Maybe a -> Maybe ar
tuplify = (a -> ar) -> Maybe a -> Maybe ar
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap a -> ar
forall l t. Tuplify l t => l -> t
tuplify
data Titled a = Titled String a
instance Tuplify a ar => Tuplify (Titled a) ar where
tuplify :: Titled a -> ar
tuplify (Titled String
_ a
a) = a -> ar
forall l t. Tuplify l t => l -> t
tuplify a
a