{-# LANGUAGE TypeOperators #-}
module Control.Applicative.Compose where
import Control.Applicative
-- | Type-level composition
newtype (f :+: g) a = Compose { decompose :: (f (g a)) }
instance (Functor f, Functor g) => Functor (f :+: g) where
fmap f (Compose x) = Compose $ (fmap . fmap) f x
{- The composition of any two Applicatives is an idiom -}
instance (Applicative f, Applicative g) => Applicative (f :+: g) where
pure x = Compose$ (pure pure) <*> (pure x)
Compose fs <*> Compose xs = Compose $ pure (<*>) <*> fs <*> xs