module Util.Cache(
Cache,
newCache,
getCached
) where
import qualified Data.Map as Map
import Control.Concurrent
data Ord key =>
Cache key elt = Cache (MVar(Map.Map key (MVar elt))) (key -> IO elt)
newCache :: Ord key => (key -> IO elt) -> IO(Cache key elt)
newCache getAct =
do
cacheMVar <- newMVar Map.empty
return (Cache cacheMVar getAct)
getCached :: Ord key => Cache key elt -> key -> IO elt
getCached (Cache cacheMVar getAct) key =
do
cacheMap <- takeMVar cacheMVar
case Map.lookup key cacheMap of
Just mVar ->
do
putMVar cacheMVar cacheMap
readMVar mVar
Nothing ->
do
mVar <- newEmptyMVar
putMVar cacheMVar (Map.insert key mVar cacheMap)
value <- getAct key
putMVar mVar value
return value