2 % (c) The GRASP/AQUA Project, Glasgow University, 1992-1997
5 \section[LazyST]{The Lazy State Transformer Monad, @LazyST@}
7 This module presents an identical interface to ST, but the underlying
8 implementation of the state thread is lazy.
18 -- ST is one, so you'll likely need some Monad bits
22 newSTRef, readSTRef, writeSTRef,
25 newSTArray, readSTArray, writeSTArray, boundsSTArray,
26 thawSTArray, freezeSTArray, unsafeFreezeSTArray,
29 strictToLazyST, lazyToStrictST
33 import qualified STBase
35 import qualified UnsafeST ( unsafeInterleaveST )
36 import PrelBase ( Eq(..), Int, Bool, ($), ()(..) )
41 newtype ST s a = ST (STBase.State s -> (a,STBase.State s))
43 instance Monad (ST s) where
45 return a = ST $ \ s -> (a,s)
46 m >> k = m >>= \ _ -> k
56 -- ToDo: un-inline this, it could cause problems...
57 runST :: (All s => ST s a) -> a
58 runST st = case st of ST st -> let (r,_) = st (STBase.S# realWorld#) in r
61 %*********************************************************
63 \subsection{Variables}
65 %*********************************************************
68 newSTRef :: a -> ST s (ST.STRef s a)
69 readSTRef :: ST.STRef s a -> ST s a
70 writeSTRef :: ST.STRef s a -> a -> ST s ()
72 newSTRef = strictToLazyST . ST.newSTRef
73 readSTRef = strictToLazyST . ST.readSTRef
74 writeSTRef r a = strictToLazyST (ST.writeSTRef r a)
77 %*********************************************************
81 %*********************************************************
84 newtype STArray s ix elt = STArray (MutableArray s ix elt)
86 newSTArray :: Ix ix => (ix,ix) -> elt -> ST s (STArray s ix elt)
87 readSTArray :: Ix ix => STArray s ix elt -> ix -> ST s elt
88 writeSTArray :: Ix ix => STArray s ix elt -> ix -> elt -> ST s ()
89 boundsSTArray :: Ix ix => STArray s ix elt -> (ix, ix)
90 thawSTArray :: Ix ix => Array ix elt -> ST s (STArray s ix elt)
91 freezeSTArray :: Ix ix => STArray s ix elt -> ST s (Array ix elt)
92 unsafeFreezeSTArray :: Ix ix => STArray s ix elt -> ST s (Array ix elt)
95 strictToLazyST (newArray ixs init) >>= \arr ->
98 readSTArray (STArray arr) ix = strictToLazyST (readArray arr ix)
99 writeSTArray (STArray arr) ix v = strictToLazyST (writeArray arr ix v)
100 boundsSTArray (STArray arr) = boundsOfArray arr
102 strictToLazyST (thawArray arr) >>= \arr ->
104 freezeSTArray (STArray arr) = strictToLazyST (freezeArray arr)
105 unsafeFreezeSTArray (STArray arr) = strictToLazyST (unsafeFreezeArray arr)
107 strictToLazyST :: STBase.ST s a -> ST s a
108 strictToLazyST (STBase.ST m) = ST $ \s ->
111 STBase.STret s2# r = m s#
115 lazyToStrictST :: ST s a -> STBase.ST s a
116 lazyToStrictST (ST m) = STBase.ST $ \s ->
117 case (m (STBase.S# s)) of (a, STBase.S# s') -> STBase.STret s' a
119 unsafeInterleaveST :: ST s a -> ST s a
120 unsafeInterleaveST = strictToLazyST . ST.unsafeInterleaveST . lazyToStrictST