Haskell - store variables -
i write simple interpreter , store variables. till have:
-- myenv map strings integers type myenv = m.map string int type tcm = errort string (statet myenv io)
i have definition
ms_assgn :: assgn -> tcm() ms_assgn (assgn (ident ident) exp) = map <- w1 <- ms_exp exp put (m.insert (ident w1 map))
and have obtained following mistatkes:
interpret.hs:118:5: couldn't match type `envnt' `a0 -> m.map k0 a0 -> m.map k0 a0' when using functional dependencies combine monadstate s (statet s m), arising dependency `m -> s' in instance declaration in `control.monad.state.class' monadstate (a0 -> m.map k0 a0 -> m.map k0 a0) (statet envnt io), arising use of `put' @ interpret.hs:118:5-7 in stmt of 'do' block: put (m.insert (ident w1 map)) in expression: { map <- get; w1 <- ms_exp exp; put (m.insert (ident w1 map)) } interpret.hs:118:20: couldn't match expected type `integer -> envnt -> k0' actual type `[char]' function `ident' applied 2 arguments, type `string' has none in first argument of `m.insert', namely `(ident w1 map)' in first argument of `put', namely `(m.insert (ident w1 map))'
when commented out last line put , replace return() makes nothing resonable, @ least compiles. ms_assgn function understand way:
- firstly current state
- next eveluate exp w1
- finanlly upadte state
what wrong it? hints?
it's set of parentheses.
m.insert (ident w1 map) -- wrong
the insert
function has type k -> -> map k -> map k a
, parentheses mean calling ident
if function.
m.insert ident w1 map -- correct
however, semantic issue, might run unexpected behavior if ms_exp exp
modifies environment, because changes lost. move above modification of environment:
ms_assgn (assgn (ident ident) exp) = w1 <- ms_exp exp map <- put $ m.insert ident w1 map
and get
followed put
can changed modify
, currying insert
. incidentally, if ever wondered why map k a
last argument insert
, reason.
ms_assgn (assgn (ident ident) exp) = w1 <- ms_exp exp modify $ m.insert ident w1
and if like, can identify 2 do
lines single >>=
, so...
ms_assgn (assgn (ident ident) exp) = ms_exp exp >>= modify . m.insert ident
you can see how, rather using imperative do
, data flows through monadic bind operator >>=
action modifies environment.
Comments
Post a Comment