The Writer Monad

class hymn.types.writer.Writer(value)

Bases: hymn.types.monad.Monad

the writer monad

computation which accumulate output along with result

bind(f)

the bind operation of Writer

execute()

extract the output of writer

run()

unwrap the writer computation

classmethod unit(value)

the unit of writer monad

hymn.types.writer.censor(f, m)

apply f to the output

hymn.types.writer.execute(self)

extract the output of writer

hymn.types.writer.listen(m)

execute m and adds its output to the value of computation

hymn.types.writer.run(self)

unwrap the writer computation

hymn.types.writer.tell(message)

log the message

hymn.types.writer.writer(value, message)

embed a writer action with value and message

hymn.types.writer.writer_m

alias of Writer

hymn.types.writer.writer_with_type(t)

create a writer for type t

hymn.types.writer.writer_with_type_of(message)

create a writer of type of message

hymn.types.writer.execute()

alias of Writer.execute()

hymn.types.writer.run()

alias of Writer.run()

Predefined Writers

class hymn.types.writer.ComplexWriter(value)
class hymn.types.writer.DecimalWriter(value)
class hymn.types.writer.FloatWriter(value)
class hymn.types.writer.FractionWriter(value)
class hymn.types.writer.ListWriter(value)
class hymn.types.writer.IntWriter(value)
hymn.types.writer.StringWriter

alias of StrWriter

class hymn.types.writer.TupleWriter(value)

Hy Specific API

writer-m

alias of Writer

Functions

writer-with-type

alias of writer_with_type()

writer-with-type-of

alias of writer_with_type_of()

Reader Macro

+ [w]

create a writer that logs w

Writers

complex-writer-m

alias of ComplexWriter

decimal-writer-m

alias of DecimalWriter

float-writer-m

alias of FloatWriter

fraction-writer-m

alias of FractionWriter

list-writer-m

alias of ListWriter

int-writer-m

alias of IntWriter

string-writer-m

alias of StringWriter

tuple-writer-m

alias of TupleWriter

Examples

Do Notation

=> (import [hymn.types.writer [tell]])
=> (require [hymn.macros [do-monad]])
=> (do-monad [_ (tell 1) _ (tell 2)] None)
IntWriter((None, 3))
=> (do-monad [_ (tell "hello ") _ (tell "world!")] None)
StrWriter((None, 'hello world!'))

Operations

writer() creates a Writer

=> (import [hymn.types.writer [writer]])
=> (writer None 1)
IntWriter((None, 1))

tell() adds message into accumulated values of writer

=> (import [hymn.types.writer [tell writer]])
=> (.run (tell 1))
(None, 1)
=> (.run (>> (writer 1 1) tell))
(None, 2)

tell() and writer() are smart enough to create writer of appropriate type

=> (import [hymn.types.writer [tell writer]])
=> (writer None "a")
StrWriter((None, 'a'))
=> (writer None 1)
IntWriter((None, 1))
=> (writer None 1.0)
FloatWriter((None, 1.0))
=> (writer None (, 1))
TupleWriter((None, (1,)))
=> (writer None [1])
ListWriter((None, [1]))
=> (tell "a")
StrWriter((None, 'a'))
=> (tell 1)
IntWriter((None, 1))
=> (tell 1.0)
FloatWriter((None, 1.0))
=> (tell (, 1))
TupleWriter((None, (1,)))
=> (tell [1])
ListWriter((None, [1]))

Use listen() to get the value of the writer

=> (import [hymn.types.writer [listen writer]])
=> (listen (writer "value" 42))
IntWriter((('value', 42), 42))

Use censor() to apply function to the output

=> (import [hymn.types.writer [censor tell]])
=> (require [hymn.macros [do-monad]])
=> (def logs (do-monad [_ (tell [1]) _ (tell [2]) _ (tell [3])] None))
=> (.execute logs)
[1, 2, 3]
=> (.execute (censor sum logs))
6

Reader Macro

=> (require [hymn.types.writer [+]])
=> ;; reader macro + works like tell
=> #+1
IntWriter((None, 1))
=> (.execute #+1)
1
=> (require [hymn.macros [do-monad]])
=> (do-monad [_ #+1 _ #+2 _ #+4] 42)
IntWriter((42, 7))