[Haskell-beginners] adding state handing to existing code

Scott Thoman scott at thoman.org
Sat Jan 23 20:36:15 EST 2010

Since I'm very new to Haskell I have what is probably a simple
question yet I'm having trouble finding a clear example of how it
works.  The basic question is: how do I pass state through existing
code without the intermediate code knowing about it.  If I have, for
example, several layers of function calls and the innermost function
needs to access some state that is only "seeded" by the outermost
function, how do I do that without the functions in between knowing
about the additional state being threaded through them?

I have a simple example (that may *not* be good idiomatic Haskell):

process ::  Integer -> Integer -> Integer
process x y =
    2 * x * y

doit :: IO ()
doit = do
    printf "f x y = %d\n" $ process 42 43

main :: IO ()
main = do
    putStrLn "done"

(I'm not totally sure about the type of "doit" but the code compiles
and runs as expected)

What I want to do is add some state handing to "process" to have it,
say, count the number of times it's been called (putting
threading/thread-local concerns aside for the moment).  I'm trying to
understand how to add state to "process" along the lines of:

process ::  Integer -> Integer -> State Integer Integer
process x y = do
    s <- get
    put $ s + 1
    return $ 2 * x * y

but I want to only seed the state from "main" without "doit" having to
change -- I can call "process" from "doit" like "(execState (process
42 43) 0)" but I want the initial state to be determined at the top
level, from main.

I have a feeling there's some kind of "ah ha" moment that I'm just not
seeing yet.  Any help or pointers to where I can look for myself would
be greatly appreciated.

Thanks in advance,


More information about the Beginners mailing list