您的问题的直接答案是:不,没有标准库提供此功能。此外,您提出的版本仍然会泄漏。我知道唯一不泄漏的版本是模拟
WriterT
使用严格的
StateT
我写了一篇非常详细的
e-mail about this to the Haskell libraries mailing list
比较了几种实现的严格性和性能。长话短说:实施
写入器T
作为一个严格的
状态T
不仅消除了空间泄漏,而且生成了非常高效的代码。
以下是有效的实施:
newtype WriterT w m a = WriterT { unWriterT :: w -> m (a, w) }
instance (Monad m, Monoid w) => Monad (WriterT w m) where
return a = WriterT $ \w -> return (a, w)
m >>= f = WriterT $ \w -> do
(a, w') <- unWriterT m w
unWriterT (f a) w'
runWriterT :: (Monoid w) => WriterT w m a -> m (a, w)
runWriterT m = unWriterT m mempty
tell :: (Monad m, Monoid w) => w -> WriterT w m ()
tell w = WriterT $ \w' ->
let wt = w `mappend` w'
in wt `seq` return ((), w `mappend` w')
我希望将此添加到
transformers
在某些情况下,但有一些小问题需要解决(例如,模块名称应该是什么)。