В теории категорий монада может быть построена из двух сопряженных функторов. В частности, если С и D - категории, а F: C → D и G: D → C - сопряженные функторы, в том смысле, что существует биекция
hom (FX, Y) = hom (X, GY)
для каждого X в C и Y в D, то композиция G o F: C → C является монадой.
Одна такая пара сопряженных функторов может быть задана путем фиксации типа b
и принятия F
и G
как
data F b a = F (a,b)
data G b a = G (b -> a)
instance Functor (F b) where
fmap f (F (a,b)) = F (f a, b)
instance Functor (G b) where
fmap f (G g) = G (f . g)
и биекция между hom-множествами задается (по модулю конструкторов) путем каррирования:
iso1 :: (F b a -> c) -> a -> G b c
iso1 f = \a -> G $ \b -> f (F (a,b))
iso2 :: (a -> G b c) -> F b a -> c
iso2 g = \(F (a,b)) -> let (G g') = g a in g' b
и в этом случае соответствующая монада
data M b a = M { unM :: b -> (a,b) }
instance Monad (M b) where
return a = M (\b -> (a,b))
(M f) >>= g = M (\r -> let (a,r') = f r in unM (g r') a)
Я не знаю, как должно быть имя этой монады, за исключением того, что это похоже на монаду-читателю, которая несет в себе часть переписываемой информации ( изменить: точки dbaupp в комментариях, что это монада State
.)
Итак, монада State
может быть "разложена" как пара сопряженных функторов F
и G
, и мы могли бы написать
State = G . F
До сих пор так хорошо.
Теперь я пытаюсь выяснить, как разложить другие общие монады на пары присоединенных функторов - например, Maybe
, []
, Reader
, Writer
, Cont
- но я не могу выяснить, какие пары сопряженных функторов мы можем "разложить" на них.
Единственный простой случай - это монада Identity
, которую можно разложить на любую пару функторов F
и G
таких, что F
обратна к G
(в частности, вы могли бы просто возьмите F = Identity
и G = Identity
).
Может ли кто-нибудь пролить свет?