TypeCompose-0.6.0: src/Data/RefMonad.hs
{-# LANGUAGE MultiParamTypeClasses, FunctionalDependencies #-}
{-# OPTIONS_GHC -Wall #-}
----------------------------------------------------------------------
-- |
-- Module : Data.RefMonad
-- Copyright : (c) Conal Elliott 2007
-- License : BSD3
--
-- Maintainer : conal@conal.net
-- Stability : experimental
-- Portability : MPTC
--
-- Monads with references, taken from John Hughes's "Global Variables in
-- Haskell" (<http://citeseer.ist.psu.edu/473734.html>).
--
----------------------------------------------------------------------
module Data.RefMonad (RefMonad(..), modifyRef) where
import Data.IORef (IORef, newIORef, readIORef, writeIORef)
import Data.STRef (STRef, newSTRef, readSTRef, writeSTRef)
import Control.Monad.ST (ST)
-------------------------------------------------------------------------------
-- | Class of monads with references.
class Monad m => RefMonad m r | m -> r where
newRef :: a -> m (r a)
readRef :: r a -> m a
writeRef :: r a -> a -> m ()
instance RefMonad IO IORef where
newRef = newIORef
readRef = readIORef
writeRef = writeIORef
instance RefMonad (ST s) (STRef s) where
newRef = newSTRef
readRef = readSTRef
writeRef = writeSTRef
-- | Change the contents of a ref
modifyRef :: RefMonad m r => r a -> (a -> a) -> m ()
modifyRef ref f = readRef ref >>= writeRef ref . f