是否有 Monad 的实例但没有 MonadFix 的实例?

2024-02-02

问题主要在标题中。这好像是mfix可以为任何单子计算定义,即使它可能会发散:

mfix :: (a -> m a) -> m a
mfix f = fix (join . liftM f)

这个构造有什么问题吗?另外,为什么Monad and MonadFix类型类是分开的(即什么类型有一个实例Monad但不属于MonadFix)?


The 左翼收缩(或收紧)法说 http://hackage.haskell.org/package/base-4.7.0.1/docs/Control-Monad-Fix.html#t:MonadFix that

mfix (\x -> a >>= \y -> f x y)  =  a >>= \y -> mfix (\x -> f x y)

特别是这意味着

mfix (\x -> a' >> f x)  =  a' >> mfix f

这意味着里面的单子动作mfix必须只评估一次。这是主要属性之一MonadFix您的版本无法满足。

考虑这个创建循环可变列表的示例(让我们忽略这样一个事实,即您可以在不使用mfix由于可变性):

import Control.Monad
import Control.Monad.Fix
import Data.IORef

data MList a = Nil | Cons a (IORef (MList a))

mrepeat :: a -> IO (MList a)
mrepeat x = mfix (liftM (Cons x) . newIORef)

main = do
    (Cons x _) <- mrepeat 1
    print x

与你的变体mfix打电话给mrepeat永远不会完成,因为你用它来称呼内部部分newIORef无限期地。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

是否有 Monad 的实例但没有 MonadFix 的实例? 的相关文章

随机推荐