acme-memorandom-0.0.1: src/System/Random/MemoRandom.hs
{-# LANGUAGE TypeFamilies #-}
{-# LANGUAGE TypeOperators #-}
-- |
-- Module : Systen.Random.MemoRandom
-- Description : Memoized random number generation
-- Copyright : © 2015 Johan Kiviniemi
-- License : MIT
-- Maintainer : Johan Kiviniemi <devel@johan.kiviniemi.name>
-- Stability : provisional
-- Portability : TypeFamilies, TypeOperators
--
-- A library for generating random numbers in a memoized manner. Implemented as
-- a lazy table indexed by serialized 'StdGen'. Monomorphism is used to
-- facilitate memoization, users should adapt their design to work with random
-- 'Int' values only.
module System.Random.MemoRandom (randomR', random') where
import Data.MemoTrie
import System.Random
newtype StdGen' = StdGen' { unStdGen' :: StdGen }
instance HasTrie StdGen' where
newtype StdGen' :->: a = StdGenTrie' (String :->: a)
trie f = StdGenTrie' (trie (f . StdGen' . read))
untrie (StdGenTrie' t) = untrie t . show . unStdGen'
enumerate (StdGenTrie' t) = [ (StdGen' (read a), b) | (a,b) <- enumerate t ]
-- | A memoized variant of 'randomR'.
randomR' :: (Int, Int) -> StdGen -> (Int, StdGen)
randomR' ival = memo2 (\ival' -> randomR ival' . unStdGen') ival . StdGen'
-- | A memoized variant of 'random'.
random' :: StdGen -> (Int, StdGen)
random' = memo (random . unStdGen') . StdGen'