函数可以是协变的和逆变的.这种协变/逆变二元性也可以应用于monad吗?
就像是:
class Monad m where
return :: a -> m a
(>>=) :: m a -> (a -> m b) -> m b
class ContraMonad m where
return :: a -> m a
contrabind :: m a -> (b -> m a) -> m b
Run Code Online (Sandbox Code Playgroud)
请问ContraMonad类有意义吗?任何例子?
从类别理论的角度来看,这个答案包括以下声明:
......事实是,co和逆变函数之间没有真正的区别,因为每个函子只是一个协变函子.
...
更详细地说,从类别C到类别D的逆变函数F只不过是F类型的(协变)函子:C op →D,从C的相反类别到类别D.
在另一方面,Haskell的Functor和Contravariant仅仅需要fmap和contramap,分别为实例来定义.这表明,从Haskell的角度来看,存在Contravariant但不是Functors的对象(反之亦然).
因此,似乎在类别理论中"co和逆变函子之间没有真正的区别",而在Haskell中,Contravariant和之间有区别Functor.
我怀疑这种差异与Haskell在Hask中发生的所有实现有关,但我不确定.
我认为我自己理解每个类别理论和Haskell的观点,但我很难找到连接两者的直觉.
嗨,我正在寻找一种允许monad堆栈跳过剩余动作的好方法,而不会完全跳过.有点像returnC系列语言.
例如,假设我正在使用monadic动作来产生副作用
type MyMonad = ??
doStuff :: MyMonad ()
doStuff = do
r <- doSomething
-- equivalent to if (r == "X") return; in C
dontGoPastHereIf (r == "X")
doSomeSideEffects r
Run Code Online (Sandbox Code Playgroud)
所以我希望它只能doSomeSideEffects在某些条件下执行.
我知道你可以做一些接近这个与guard和when了.虽然可以没有嵌套吗?
ExceptT已允许您退出正常流程并返回早期结果.但是ExceptT错误/跳过会传播.我想只跳过本地函数中的其余步骤
doTwoSteps :: MyMonad ()
doTwoSteps = do
-- if I used ExceptT, an error in the first function will skip the second.
-- But I still want to do the second step here
doStuff …Run Code Online (Sandbox Code Playgroud)