每隔单子配有变压器的版本,从我知道变压器的想法是单子的通用扩展。 继给其他变压器建设, IOT
会是这样的
newtype IOT m a = IOT { runIOT :: m (IO a) }
为此,我可以弥补当场有用的应用: IOT Maybe
可以做一个IO动作或没有, IOT []
可以建立以后可以列表sequence
d。
那么,为什么会出现在Haskell没有IO变压器?
(注:我已经看到了在咖啡厅的Haskell这个职位 ,但不能做它多大意义也。 为ST变压器Hackage页提到了其描述一个可能相关的问题,但没有提供任何细节。)
考虑的具体例子IOT Maybe
。 你会如何写一个Monad
该实例? 你可以像这样的东西开始:
instance Monad (IOT Maybe) where
return x = IOT (Just (return x))
IOT Nothing >>= _ = IOT Nothing
IOT (Just m) >>= k = IOT $ error "what now?"
where m' = liftM (runIOT . k) m
现在你有m' :: IO (Maybe (IO b))
但你需要类型的东西Maybe (IO b)
其中-最重要的-之间的选择Just
和Nothing
应予以确定m'
。 如何将这项实施?
答案当然是它不会,因为它不能。 你也可以证明一个unsafePerformIO
在里面,隐藏着一个纯粹的接口后面,因为从根本上你问一个纯粹的价值-的选择Maybe
构造-依赖的东西中的结果IO
。 Nnnnnope,不会发生的。
这种情况甚至在一般情况下更糟,因为一个任意(通用量化) Monad
更是不可能解开比IO
是。
顺便说一句, ST
你提到的变压器从您的建议不同的方式实现IOT
。 它采用内部实行ST
的State
使用编译器提供的魔法精灵之尘特殊的原语般的单子,并定义了StateT
基于该式变压器。 IO
在内部实现为一个更神奇的ST
,因此假设的IOT
可以以类似的方式来定义。
不,这真的改变任何东西,除了可能让你过的不纯所造成的副作用相对顺序更好的控制IOT
。