
On Sat, Jan 9, 2010 at 2:23 AM, Alexei Kitaev
Reading the discussion related to your blog, I realized that strict State is different in that it does not actually force the state. But forcing can be achieved by wrapping all actions with the following function:
sState :: (s -> (a,s)) -> State s a sState f = State $ \s -> case f s of (a,s') -> s' `seq` (a,s')
I hope that somebody will answer my other questions about the operational semantics and optimizations.
Hi Alexei, you have a ton of great points but I wanted to discuss an issue with this one. It's unusual that this is what you want either; since it only reduces the state to WHNF. For example, if your state is a string, this only evaluates enough to know whether or not the string is empty at each step, and you can still get into trouble with code like this: put ("xxx" ++ some_bad_computation) which leave bottoms inside of your state which won't show up until later. Several attempts to solve this problem exist, but the most commonly used one is the "rnf" strategy from Control.Parallel.Strategies, which uses a typeclass to allow each type to specify how to evaluate itself completely. -- ryan