module Data.Profunctor.Representable
( RepresentableProfunctor(..)
) where
import Data.Functor
import Data.Functor.Identity
import Data.Functor.Compose
import Data.Profunctor
import Data.Profunctor.Composition
import Control.Comonad
class (Profunctor k, Functor (Rep k)) => RepresentableProfunctor k where
type Rep k :: * -> *
tabulatePro :: (Rep k d -> c) -> k d c
indexPro :: k d c -> Rep k d -> c
instance RepresentableProfunctor (->) where
type Rep (->) = Identity
tabulatePro f = f . Identity
indexPro f (Identity d) = f d
instance Functor w => RepresentableProfunctor (Cokleisli w) where
type Rep (Cokleisli w) = w
tabulatePro = Cokleisli
indexPro = runCokleisli
instance Functor f => RepresentableProfunctor (DownStar f) where
type Rep (DownStar f) = f
tabulatePro = DownStar
indexPro = runDownStar
instance (RepresentableProfunctor f, RepresentableProfunctor g) => RepresentableProfunctor (Procompose f g) where
type Rep (Procompose f g) = Compose (Rep g) (Rep f)
tabulatePro f = Procompose (tabulatePro id) (tabulatePro (f . Compose))
indexPro (Procompose f g) (Compose d) = indexPro g $ indexPro f <$> d