Se reclamó en Validations in Haskell que el uso de un Writer
garantiza la concatenación asociativa derecha. Sin embargo, este ejemplo parece mostrar lo contrario. ¿Cuál es la respuesta correcta?¿Writer Monad garantiza la concatenación asociativa correcta?
{-# 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
Produce:
"Hello" ++ ("World" ++ "World" ++ "") ++ "!"
+1 para el ejemplo simple de usar e implementar 'showsPrec'. –
Curiosamente, si reemplaza 'replicateM_' con' replicateM', la salida se convierte en '" Hello "++ (" World "++ (" World "++" "++" ") ++" ") ++" ! "' – pat
Es la diferencia entre 'sequence' y' sequence_': 'sequence = foldr (liftM2 (:)) (return [])' pero 'sequence_ = foldr (>>) (return())'; el primero genera más ataduras porque hace cosas con los resultados. – ehird