on 8a63c15 help sign in
58 lines 1.4 kB history raw
1-- | The 'State' as an effect.
2--
3-- Represented as a pure value underneath, therefore:
4--
5-- - very fast
6--
7-- - not suitable for sharing between multiple threads.
8--
9-- If you plan to do the latter, have a look at "Effective.State.MVar" or
10-- "Effective.State.Dynamic".
11--
12module Effectful.State
13 ( State
14 , runState
15 , evalState
16 , execState
17 , get
18 , put
19 , state
20 , modify
21 , stateM
22 , modifyM
23 ) where
25import Data.Coerce
27import Effectful.Internal.Has
28import Effectful.Internal.Monad
30-- | Provide access to a pure, mutable state of type @s@.
31newtype State s = State { unState :: s }
33runState :: s -> Eff (State s : es) a -> Eff es (a, s)
34runState s = coerce . runEffect (State s)
36evalState :: s -> Eff (State s : es) a -> Eff es a
37evalState s = evalEffect (State s)
39execState :: s -> Eff (State s : es) a -> Eff es s
40execState s = coerce . execEffect (State s)
42get :: State s :> es => Eff es s
43get = unState <$> getEffect
45put :: State s :> es => s -> Eff es ()
46put = putEffect . State
48state :: State s :> es => (s -> (a, s)) -> Eff es a
49state f = stateEffect $ \(State s0) -> let (a, s) = f s0 in (a, State s)
51modify :: State s :> es => (s -> s) -> Eff es ()
52modify f = state (\s -> ((), f s))
54stateM :: State s :> es => (s -> Eff es (a, s)) -> Eff es a
55stateM f = stateEffectM $ \(State s0) -> coerce $ f s0
57modifyM :: State s :> es => (s -> Eff es s) -> Eff es ()
58modifyM f = stateM (\s -> ((), ) <$> f s)