{-# OPTIONS --cubical-compatible --safe #-}
module Effect.Applicative where
open import Data.Bool.Base using (Bool; true; false)
open import Data.Product.Base using (_×_; _,_)
open import Data.Unit.Polymorphic.Base using (⊤)
open import Effect.Choice using (RawChoice)
open import Effect.Empty using (RawEmpty)
open import Effect.Functor as Fun using (RawFunctor)
open import Function.Base using (const; flip; _∘′_)
open import Level using (Level; suc; _⊔_)
open import Relation.Binary.PropositionalEquality.Core using (_≡_)
private
variable
f g : Level
A B C : Set f
record RawApplicative (F : Set f → Set g) : Set (suc f ⊔ g) where
infixl 4 _<*>_ _<*_ _*>_
infixl 4 _⊛_ _<⊛_ _⊛>_
infix 4 _⊗_
field
rawFunctor : RawFunctor F
pure : A → F A
_<*>_ : F (A → B) → F A → F B
open RawFunctor rawFunctor public
_<*_ : F A → F B → F A
a <* b = const <$> a <*> b
_*>_ : F A → F B → F B
a *> b = flip const <$> a <*> b
zipWith : (A → B → C) → F A → F B → F C
zipWith f x y = f <$> x <*> y
zip : F A → F B → F (A × B)
zip = zipWith _,_
return : A → F A
return = pure
_⊛_ : F (A → B) → F A → F B
_⊛_ = _<*>_
_<⊛_ : F A → F B → F A
_<⊛_ = _<*_
_⊛>_ : F A → F B → F B
_⊛>_ = _*>_
_⊗_ : F A → F B → F (A × B)
_⊗_ = zip
module _ where
open RawApplicative
open RawFunctor
mkRawApplicative :
(F : Set f → Set g) →
(pure : ∀ {A} → A → F A) →
(app : ∀ {A B} → F (A → B) → F A → F B) →
RawApplicative F
mkRawApplicative F pure app .rawFunctor ._<$>_ = app ∘′ pure
mkRawApplicative F pure app .pure = pure
mkRawApplicative F pure app ._<*>_ = app
record RawApplicativeZero (F : Set f → Set g) : Set (suc f ⊔ g) where
field
rawApplicative : RawApplicative F
rawEmpty : RawEmpty F
open RawApplicative rawApplicative public
open RawEmpty rawEmpty public
guard : Bool → F ⊤
guard true = pure _
guard false = empty
record RawAlternative (F : Set f → Set g) : Set (suc f ⊔ g) where
field
rawApplicativeZero : RawApplicativeZero F
rawChoice : RawChoice F
open RawApplicativeZero rawApplicativeZero public
open RawChoice rawChoice public
record Morphism {F₁ F₂ : Set f → Set g}
(A₁ : RawApplicative F₁)
(A₂ : RawApplicative F₂) : Set (suc f ⊔ g) where
module A₁ = RawApplicative A₁
module A₂ = RawApplicative A₂
field
functorMorphism : Fun.Morphism A₁.rawFunctor A₂.rawFunctor
open Fun.Morphism functorMorphism public
field
op-pure : (x : A) → op (A₁.pure x) ≡ A₂.pure x
op-<*> : (f : F₁ (A → B)) (x : F₁ A) →
op (f A₁.⊛ x) ≡ (op f A₂.⊛ op x)
op-⊛ = op-<*>