module Pandora.Paradigm.Controlflow.Effect.Interpreted where

import Pandora.Pattern.Category ((.))
import Pandora.Pattern.Functor.Covariant (Covariant)
import Pandora.Pattern.Transformer.Liftable (Liftable (lift))
import Pandora.Paradigm.Primary.Functor.Function ()

type family Schematic (c :: (* -> *) -> k) (t :: * -> *) = (r :: (* -> *) -> * -> *) | r -> t

class Interpreted t where
	{-# MINIMAL run, unite #-}
	type Primary t a :: *
	run :: t a -> Primary t a
	unite :: Primary t a -> t a

	(||=) :: Interpreted u => (Primary t a -> Primary u b) -> t a -> u b
	(||=) Primary t a -> Primary u b
f = Primary u b -> u b
forall (t :: * -> *) a. Interpreted t => Primary t a -> t a
unite (Primary u b -> u b) -> (t a -> Primary u b) -> t a -> u b
forall (m :: * -> * -> *) b c a.
Category m =>
m b c -> m a b -> m a c
. Primary t a -> Primary u b
f (Primary t a -> Primary u b)
-> (t a -> Primary t a) -> t a -> Primary u b
forall (m :: * -> * -> *) b c a.
Category m =>
m b c -> m a b -> m a c
. t a -> Primary t a
forall (t :: * -> *) a. Interpreted t => t a -> Primary t a
run

	(=||) :: Interpreted u => (t a -> u b) -> Primary t a -> Primary u b
	(=||) t a -> u b
f = u b -> Primary u b
forall (t :: * -> *) a. Interpreted t => t a -> Primary t a
run (u b -> Primary u b)
-> (Primary t a -> u b) -> Primary t a -> Primary u b
forall (m :: * -> * -> *) b c a.
Category m =>
m b c -> m a b -> m a c
. t a -> u b
f (t a -> u b) -> (Primary t a -> t a) -> Primary t a -> u b
forall (m :: * -> * -> *) b c a.
Category m =>
m b c -> m a b -> m a c
. Primary t a -> t a
forall (t :: * -> *) a. Interpreted t => Primary t a -> t a
unite

(-=:) :: (Liftable t, Interpreted (t u), Interpreted (t v), Covariant u)
	=> (t u a -> t v b) -> u a -> Primary (t v) b
-=: :: (t u a -> t v b) -> u a -> Primary (t v) b
(-=:) t u a -> t v b
f = t v b -> Primary (t v) b
forall (t :: * -> *) a. Interpreted t => t a -> Primary t a
run (t v b -> Primary (t v) b)
-> (u a -> t v b) -> u a -> Primary (t v) b
forall (m :: * -> * -> *) b c a.
Category m =>
m b c -> m a b -> m a c
. t u a -> t v b
f (t u a -> t v b) -> (u a -> t u a) -> u a -> t v b
forall (m :: * -> * -> *) b c a.
Category m =>
m b c -> m a b -> m a c
. u a -> t u a
forall (t :: (* -> *) -> * -> *) (u :: * -> *).
(Liftable t, Covariant u) =>
u ~> t u
lift