On Wed, May 21, 2008 at 11:10 AM, Dmitri O.Kondratiev <[EMAIL PROTECTED]>
wrote:

> But how will 'g1' actually get delivered from 'makeRandomValueST g1' to
> invocation of 'getAny' I don't yet understand!
>
>
It may be easier to understand the state passing if you remove the do
notation and replace get, put and return with their definition in the
instance declarations (Monad and MonadState).

getAny :: (Random a) => State StdGen a
getAny = do g      <- get
            (x,g') <- return $ random g
            put g'
            return x

get = State $ \s -> (s, s) -- copy the state as a return value and pass
state
put s = State $ \_ -> ((), s) -- return unit, ignore the passed state and
replace it with the state given as parameter.
return a = State $ \s -> (a, s) -- return given value and pass state.

getAnyNoSugar :: (Random a) => State StdGen a
getAnyNoSugar = (State $ \s -> (s, s)) >>= \g ->
                (State $ \s -> (random g, s)) >>= \(x,g') ->
                (State $ \_ -> ((), g')) >>
                (State $ \s -> (x, s))

The function is still useable this way and the state transformations should
be a bit more visible. The first element of the tuple is the value that will
be used to call the next function (of type Monad m => a -> m b). The second
element of the tuple is the state and the (>>=) operator will handle passing
it between actions.

Desugaring the (>>=) and (>>) operators would give you something like this
(I replaced `s` with `y` in the `put` and `return` desugaring and simplified
it):

State $ \s = let
  (g, s') = (\y -> (y,y)) s
  ((x,g'), s'') = (\y -> (random g, y)) s'
  (_, s''') = (\_ -> ((), g')) s''
  in (x, s''')

Which is explict state passing between function calls. Extract the State
using `runState`, run it with an initial state and it should give you the
expected result.

Regards,

Olivier.
_______________________________________________
Haskell-Cafe mailing list
[email protected]
http://www.haskell.org/mailman/listinfo/haskell-cafe

Reply via email to