module Data.Function.Variadic
(
Function (..),
ConstructFunction,
DeconstructFunction,
EmptyConstraint,
type (&),
)
where
import Data.Kind (Type)
class
(ConstructFunction args r ~ f, DeconstructFunction f ~ '(args, r)) =>
Function f args r argC
where
createFunction ::
proxy argC ->
(forall a. argC a => acc -> a -> acc) ->
(acc -> r) ->
acc ->
f
transformFunction ::
proxy argC ->
(forall a. argC a => acc -> a -> acc) ->
(acc -> r0 -> r) ->
acc ->
ConstructFunction args r0 ->
f
type family DeconstructFunction (f :: Type) :: ([Type], Type) where
DeconstructFunction (a -> f) = MapFst ((:) a) (DeconstructFunction f)
DeconstructFunction x = '( '[], x)
type family MapFst (f :: k1 -> k1) (tuple :: (k1, k2)) where
MapFst f '(a, b) = '(f a, b)
type family ConstructFunction (args :: [Type]) (r :: Type) where
ConstructFunction '[] r = r
ConstructFunction (a : args) r = a -> ConstructFunction args r
instance
('( '[], r) ~ DeconstructFunction r) =>
Function r '[] r argC
where
createFunction :: proxy argC
-> (forall a. argC a => acc -> a -> acc) -> (acc -> r) -> acc -> r
createFunction proxy argC
_ forall a. argC a => acc -> a -> acc
_ acc -> r
fr acc
r = acc -> r
fr acc
r
transformFunction :: proxy argC
-> (forall a. argC a => acc -> a -> acc)
-> (acc -> r0 -> r)
-> acc
-> ConstructFunction '[] r0
-> r
transformFunction proxy argC
_ forall a. argC a => acc -> a -> acc
_ acc -> r0 -> r
fr acc
acc ConstructFunction '[] r0
r = acc -> r0 -> r
fr acc
acc r0
ConstructFunction '[] r0
r
instance
(Function f args r argC, argC a) =>
Function (a -> f) (a : args) r argC
where
createFunction :: proxy argC
-> (forall a. argC a => acc -> a -> acc)
-> (acc -> r)
-> acc
-> a
-> f
createFunction proxy argC
pArgC forall a. argC a => acc -> a -> acc
fa acc -> r
fr acc
acc = proxy argC
-> (forall a. argC a => acc -> a -> acc) -> (acc -> r) -> acc -> f
forall f (args :: [*]) r (argC :: * -> Constraint)
(proxy :: (* -> Constraint) -> *) acc.
Function f args r argC =>
proxy argC
-> (forall a. argC a => acc -> a -> acc) -> (acc -> r) -> acc -> f
createFunction proxy argC
pArgC forall a. argC a => acc -> a -> acc
fa acc -> r
fr (acc -> f) -> (a -> acc) -> a -> f
forall b c a. (b -> c) -> (a -> b) -> a -> c
. acc -> a -> acc
forall a. argC a => acc -> a -> acc
fa acc
acc
transformFunction :: proxy argC
-> (forall a. argC a => acc -> a -> acc)
-> (acc -> r0 -> r)
-> acc
-> ConstructFunction (a : args) r0
-> a
-> f
transformFunction proxy argC
pArgC forall a. argC a => acc -> a -> acc
fa acc -> r0 -> r
fr acc
acc ConstructFunction (a : args) r0
f = \a
a -> proxy argC
-> (forall a. argC a => acc -> a -> acc)
-> (acc -> r0 -> r)
-> acc
-> ConstructFunction args r0
-> f
forall f (args :: [*]) r (argC :: * -> Constraint)
(proxy :: (* -> Constraint) -> *) acc r0.
Function f args r argC =>
proxy argC
-> (forall a. argC a => acc -> a -> acc)
-> (acc -> r0 -> r)
-> acc
-> ConstructFunction args r0
-> f
transformFunction proxy argC
pArgC forall a. argC a => acc -> a -> acc
fa acc -> r0 -> r
fr (acc -> a -> acc
forall a. argC a => acc -> a -> acc
fa acc
acc a
a) (ConstructFunction (a : args) r0
a -> ConstructFunction args r0
f a
a)
class EmptyConstraint a
instance EmptyConstraint a
class (f x, g x) => (&) f g (x :: k)
instance (f x, g x) => (&) f g x