A few days ago I had to randomly choose and element of a list and continue execution, so here's what I did:
I made a infinite list of Random numbers [Int] (Not IO [Int]) and I passed it around all the time in a Tuple and whenever I returned I also returned the list, so I would always have it available whenever I needed to use it. Whenever I used it I took it's head off and returned the tail, along with whatever else I was returning in a Tuple. The seed for the Random Generator was the CPUTime. Here's the code: (The function that returns the infinite list is infinito, the one on the bottom)
import Random
import CPUTime
import System.IO.Unsafe
{-|
La funcion @rand@ Retorna una lista de numeros Random para ser utilizados en la seleccion de
las guardias en los if y los do
-}
rand :: (RandomGen g, Random a) => (a,a) -> g -> [a]
rand range gen = as
where (a,b) = split gen -- create two separate generators
as = randomRs range a -- one infinite list of randoms
{-|
@seed@ Retorna la semilla con la que la funcion Random va a iniciar la generacion de los numeros Randoms
-}
seed :: Int
seed = fromInteger (unsafePerformIO getCPUTime)
{-|
@mygen@ Retorna el generador estandar con la semilla dada por la funcion @seed@
-}
mygen = mkStdGen seed
{-|
@infinito@ Retorna la lista infinita de donde se van a sacar los numeros para elegir la guardia a ser ejecutada en los if y los do
-}
infinito:: (Num t,Random t) => [t]
infinito = [ x | x <- rand (1,1000000) mygen]
Hope it works for you!
Hector Guilarte