1 module Symantic.Dityped.Algebrable where
3 import Data.Either (Either)
4 import Data.Function ((.))
5 import Data.Maybe (Maybe(..))
6 import Data.Proxy (Proxy(..))
7 import GHC.Generics (Generic)
9 import Symantic.Utils.ADT
10 import Symantic.Utils.CurryN
11 import Symantic.Dityped.Composable
12 import Symantic.Dityped.Transformable
14 -- | @('adt' @@SomeADT some_expr)@
15 -- wrap\/unwrap @(some_expr)@ input\/output value
16 -- to\/from the Algebraic Data Type @(SomeADT)@.
17 -- @(SomeADT)@ must have a 'Generic' instance
18 -- (using the @DeriveGeneric@ language extension to GHC).
25 repr (EoT (ADT adt) -> k) k ->
27 adt = dimap adtOfeot eotOfadt
30 class Tupable repr where
31 (<:>) :: repr (a->k) k -> repr (b->k) k -> repr ((a,b)->k) k
34 Liftable2 repr => Tupable (Unlifted repr) =>
35 repr (a->k) k -> repr (b->k) k -> repr ((a,b)->k) k
38 -- ** Class 'Unitable'
39 class Unitable repr where
40 unit :: repr (() -> k) k
43 unit :: Liftable repr => Unitable (Unlifted repr) =>
46 -- ** Class 'Constant'
47 class Constant repr where
48 constant :: a -> repr (a -> k) k
49 constant = lift . constant
51 Liftable repr => Constant (Unlifted repr) =>
54 -- * Class 'Eitherable'
55 class Eitherable repr where
56 (<+>) :: repr (a->k) k -> repr (b->k) k -> repr (Either a b->k) k
59 Liftable2 repr => Eitherable (Unlifted repr) =>
60 repr (a->k) k -> repr (b->k) k -> repr (Either a b -> k) k
61 -- NOTE: yes infixr, not infixl like <|>,
62 -- in order to run left-most checks first.
65 -- ** Class 'Emptyable'
66 class Emptyable repr where
70 Liftable repr => Emptyable (Unlifted repr) =>
73 -- ** Class 'Optionable'
74 class Optionable repr where
75 option :: repr k k -> repr k k
78 Liftable1 repr => Optionable (Unlifted repr) =>
80 optional :: repr (a->k) k -> repr (Maybe a->k) k
81 optional = lift1 optional
83 Liftable1 repr => Optionable (Unlifted repr) =>
84 repr (a->k) k -> repr (Maybe a->k) k
86 -- * Class 'Repeatable'
87 class Repeatable repr where
88 many0 :: repr (a->k) k -> repr ([a]->k) k
91 Liftable1 repr => Repeatable (Unlifted repr) =>
92 repr (a->k) k -> repr ([a]->k) k
93 many1 :: repr (a->k) k -> repr ([a]->k) k
96 Liftable1 repr => Repeatable (Unlifted repr) =>
97 repr (a->k) k -> repr ([a]->k) k
99 -- * Class 'Substractable'
100 class Substractable repr where
101 (<->) :: repr a k -> repr k' k' -> repr a k
104 Liftable2 repr => Substractable (Unlifted repr) =>
105 repr a k -> repr k' k' -> repr a k
108 -- * Class 'Dicurryable'
109 class Dicurryable repr where
113 (args-..->r) -> -- construction
114 (r->Tuples args) -> -- destruction
115 repr (args-..->k) k ->
117 dicurry args constr destr = lift1 (dicurry args constr destr)
120 Dicurryable (Unlifted repr) =>
125 repr (args-..->k) k ->
129 forall args a k repr.
134 Tuples args ~ EoT (ADT a) =>
135 (args ~ Args (args-..->a)) =>
137 repr (args-..->k) k ->
139 construct f = dicurry (Proxy::Proxy args) f eotOfadt