1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37
|
{-# LANGUAGE CPP, ScopedTypeVariables #-}
-- If we instead commute the monad transformers we can change the
-- reader value observed by a continuation.
import Control.Monad.Cont as C
import qualified Control.Monad.Reader as R
import Data.IORef
import Text.Printf
type M a = C.ContT () (R.ReaderT Int IO) a
test ref = do
x <- R.ask
liftIO$ printf "Observed value %d before callCC\n" x
callCC$ \cont -> do
liftIO$ writeIORef ref cont
liftIO$ printf "Write ioref inside callcc...\n"
z <- R.ask
liftIO$ printf "Observed value %d in invoked continuation\n" z
return ()
main = do ref :: IORef (() -> M ()) <- newIORef (error "should not be used")
let m0 = test ref
m1 = C.runContT m0 (\ () -> return ())
m2 = R.runReaderT m1 (100::Int)
m2
k <- readIORef ref
let m3 = do
w <- lift$ R.ask
liftIO$ putStrLn ("In new runReader instance: observed " ++ show w)
k ()
liftIO$ putStrLn " !! Should not reach here..."
R.runReaderT (C.runContT m3 (\ () -> return ())) 200
putStrLn "Done with main."
|