Writer Monad是否保证正确的关联级联? [英] Does Writer Monad guarantee right associative concatenation?

查看:136
本文介绍了Writer Monad是否保证正确的关联级联?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

它在 Haskell中的验证中声明使用 Writer 保证右关联级联。但是,这个例子似乎表明了其他情况。什么是正确答案?

It was claimed in Validations in Haskell that use of a Writer guarantees right-associative concatenation. However, this example seems to show otherwise. What's the correct answer?

{-# LANGUAGE OverloadedStrings #-}

import Control.Monad.Writer
import Data.String

data TM = TMempty
        | TMappend TM TM
        | TMfromString String

instance IsString TM where
  fromString = TMfromString

instance Monoid TM where
  mempty  = TMempty
  mappend = TMappend

instance Show TM where
  showsPrec d TMempty = showString "\"\""
  showsPrec d (TMfromString s) = showString $ show s
  showsPrec d (TMappend a b) = showParen (d > 0) $
    showsPrec 1 a .
    showString " ++ " .
    showsPrec 0 b

theWriter :: Writer TM ()
theWriter = do
  tell "Hello"
  replicateM_ 2 $ tell "World"
  tell "!"

main = print $ execWriter theWriter

生成:

"Hello" ++ ("World" ++ "World" ++ "") ++ "!"


推荐答案

是的,这确实是不真实的。从源代码

Yes, this is indeed untrue. From the source code:

m >>= k  = WriterT $ do
    ~(a, w)  <- runWriterT m
    ~(b, w') <- runWriterT (k a)
    return (b, w `mappend` w')

...

-- | @'tell' w@ is an action that produces the output @w@.
tell :: (Monoid w, Monad m) => w -> WriterT w m ()
tell w = WriterT $ return ((), w)

mappend 的链将反映(>> =) s的链。

So the chain of mappends will mirror the chain of (>>=)s.

这篇关于Writer Monad是否保证正确的关联级联?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆