monad 范畴上的函子是什么?

Fre*_*ler 8 monads haskell monad-transformers category-theory

注意,这个问题不是关于“内函子范畴的幺半群”。也不是直接关于Functors (aMonad总是 a Functor,但这个问题主要关注 monad 变压器)


Haskell 的monad 转换器上的文档SelectT指出

SelectT 不是 monad 范畴的函子,许多操作不能通过它解除。

  1. monad类别是什么?该类别中的箭头是什么?
  2. 为什么有些单子变压器上的单子(类别函子MaybeTRWST等),但有些不是(ContTSelectT)?
  3. 从编程的角度来看,成为 monad 范畴的函子有什么好处?作为图书馆的消费者,我为什么要关心?

Jon*_*rdy 4

\n
    \n
  1. 单子的类别是什么?该类别中的箭头是什么?
  2. \n
\n
\n

对象是单子的类别,即具有实例T的类型,箭头是其底层函子之间的自然转换,通常在 Haskell 中由类型函数表示(尽管严格来说参数性是比自然性更强的条件)。Type -> TypeMonadA -> Bforall x. A x -> B x

\n

mmorph包中有\xe2\x80\x99s 的实现。

\n

这一类别中的初始对象是Identity,因为对于任何 monad 来说,T都有\xe2\x80\x99s 恰好是一个自然变换forall x. Identity x -> T x。双重的,我认为最终的对象是Const ()

\n
\n
    \n
  1. 为什么有些 monad 转换器函子属于 monad 类别(MaybeTRWST等),而有些则不是(ContTSelectT)?
  2. \n
\n
\n

此类别中的函子需要提升fmap

\n
fmap\'\n  :: forall m n. (Monad m, Monad n)\n  => (forall x. m x -> n x) -> forall x. T m x -> T n x\n
Run Code Online (Sandbox Code Playgroud)\n

您可以\xe2\x80\x99t 为ContT和实现这一点SelectT。I\xe2\x80\x99m 不确定确切的原因,但它似乎取决于方差:我们\xe2\x80\x99re 试图实现一个协变函子,但ContT和在其底层单子中SelectT不变的,例如,m同时出现正数和负数在(a -> m r) -> m r里面a ContT r m a.

\n
\n
    \n
  1. 从编程的角度来看,成为 monad 范畴的函子有什么好处呢?作为图书馆的消费者,我为什么要关心?
  2. \n
\n
\n

如果您有一种通用方法 \xe2\x80\x9crun\xe2\x80\x9d a monad min a monad n,则可以\xe2\x80\x99t 将其提升为ContTor SelectT;你\xe2\x80\x99 陷入了更受限制的映射操作,如下所示:

\n
mapSelectT :: (m a -> m a) -> SelectT r m a -> SelectT r m a\nmapContT   :: (m r -> m r) -> ContT   r m a -> ContT   r m a\n
Run Code Online (Sandbox Code Playgroud)\n

底层 monad 和结果类型是固定的。因此,您可以\xe2\x80\x99t始终在使用这些转换器的堆栈中自由提升操作。

\n