0 | module Control.Category.Monoidal
2 | import Control.Category.Core
3 | import Control.Category.Functor
4 | import Data.Morphisms
7 | import Data.Singleton
31 | interface (Category cat,
CatEndoBifunctor cat ten) =>
32 | Monoidal (0 cat : Hom obj) (ten : obj -> obj -> obj) (i : obj) | cat,ten where
33 | constructor MkMonoidal
35 | assoc : {a,b,c : _} -> cat ((a `ten` b) `ten` c) (a `ten` (b `ten` c))
37 | assoc' : {a,b,c : _} -> cat (a `ten` (b `ten` c)) ((a `ten` b) `ten` c)
40 | unitl : {a : _} -> cat (i `ten` a) a
42 | unitl' : {a : _} -> cat a (i `ten` a)
45 | unitr : {a : _} -> cat (a `ten` i) a
47 | unitr' : {a : _} -> cat a (a `ten` i)
56 | PreMonoidal : (cat : Hom obj) -> (ten : obj -> obj -> obj) -> (i : obj) -> Type
57 | PreMonoidal = Monoidal
68 | TenSeq : (ten : obj -> obj -> obj) -> (i : obj) -> List obj -> obj
71 | TenSeq ten i (o :: os@(_ :: _)) = o `ten` TenSeq ten i os
75 | splitAssoc : Monoidal cat ten i => {xs,ys : _} ->
76 | cat (TenSeq ten i (xs ++ ys)) (TenSeq ten i xs `ten` TenSeq ten i ys)
77 | splitAssoc @{c@(MkMonoidal {})} {xs=[]} = unitl'
78 | splitAssoc @{c@(MkMonoidal {})} {xs=[_],ys=[]} = unitr'
79 | splitAssoc @{c@(MkMonoidal {})} {xs=[_],ys=_::_} = id
80 | splitAssoc @{c@(MkMonoidal {})} {xs=[_,_],ys=_::_} = assoc'
81 | splitAssoc @{c@(MkMonoidal {})} {xs=_::_::_} = assoc' . mapr' splitAssoc
85 | mergeAssoc : Monoidal cat ten i => {xs,ys : _} ->
86 | cat (TenSeq ten i xs `ten` TenSeq ten i ys) (TenSeq ten i (xs ++ ys))
87 | mergeAssoc @{c@(MkMonoidal {})} {xs=[]} = unitl
88 | mergeAssoc @{c@(MkMonoidal {})} {xs=[_],ys=[]} = unitr
89 | mergeAssoc @{c@(MkMonoidal {})} {xs=[_],ys=_::_} = id
90 | mergeAssoc @{c@(MkMonoidal {})} {xs=[_,_],ys=_::_} = assoc
91 | mergeAssoc @{c@(MkMonoidal {})} {xs=_::_::_} = mapr' mergeAssoc . assoc
95 | applyAssoc : Monoidal cat ten i => {xs,ys,ys',zs : _} ->
96 | cat (TenSeq ten i ys) (TenSeq ten i ys') ->
97 | cat (TenSeq ten i (xs ++ ys ++ zs)) (TenSeq ten i (xs ++ ys' ++ zs))
98 | applyAssoc @{c@(MkMonoidal {})} f =
99 | mergeAssoc . mapr' (mergeAssoc . mapl' f . splitAssoc) . splitAssoc
113 | [MorFromTensor] {ten,i : _} -> Tensor ten i => Monoidal Morphism ten i
114 | using CatBifunctor.MorFromBifunctor where
116 | assoc' = Mor assocl
117 | unitl = Mor unitl.leftToRight
118 | unitl' = Mor unitl.rightToLeft
119 | unitr = Mor unitr.leftToRight
120 | unitr' = Mor unitr.rightToLeft
125 | [FuncFromTensor] {ten,i : _} -> Tensor ten i => Monoidal (~~>) ten i
126 | using Category.Function CatBifunctor.FuncFromBifunctor where
127 | assoc = Tensor.assocr
128 | assoc' = Tensor.assocl
129 | unitl = Tensor.unitl.leftToRight
130 | unitl' = Tensor.unitl.rightToLeft
131 | unitr = Tensor.unitr.leftToRight
132 | unitr' = Tensor.unitr.rightToLeft
141 | [KleisliFromTensor] {ten,i : _} ->(Tensor ten i, Bitraversable ten, Monad m) =>
142 | Monoidal (Kleislimorphism m) ten i using KleisliFromBitraversable where
143 | assoc = Kleisli $
Prelude.pure . assocr
144 | assoc' = Kleisli $
Prelude.pure . assocl
145 | unitl = Kleisli $
Prelude.pure . unitl.leftToRight
146 | unitl' = Kleisli $
Prelude.pure . unitl.rightToLeft
147 | unitr = Kleisli $
Prelude.pure . unitr.leftToRight
148 | unitr' = Kleisli $
Prelude.pure . unitr.rightToLeft
152 | FuncPair : Monoidal (~~>) Pair ()
153 | FuncPair = FuncFromTensor
156 | FuncEither : Monoidal (~~>) Either Void
157 | FuncEither = FuncFromTensor
160 | public export %hint
161 | MonoidalMorPair : Monoidal Morphism Pair ()
162 | MonoidalMorPair = MorFromTensor
164 | public export %hint
165 | MonoidalMorEither : Monoidal Morphism Either Void
166 | MonoidalMorEither = MorFromTensor
169 | public export %hint
170 | MonoidalKleisliPair : Monad m => PreMonoidal (Kleislimorphism m) Pair ()
171 | MonoidalKleisliPair = KleisliFromTensor
173 | public export %hint
174 | MonoidalKleisliEither : Monad m => Monoidal (Kleislimorphism m) Either Void
175 | MonoidalKleisliEither = KleisliFromTensor