monty.hs (1058B)
1 import System.Random.MWC 2 import Control.Monad 3 4 data Choice = Switch | Stay deriving Eq 5 6 monty switch g = do 7 z0 <- uniformR (0, 2) g :: IO Int 8 return $ if switch then z0 /= 2 else z0 == 2 9 10 montyRandSwitch g = do 11 z0 <- uniformR (0, 2) g :: IO Int 12 zc <- uniformR (0, 1) g :: IO Double 13 let switch = zc < 0.5 14 return $ if switch then (z0 /= 2, Switch) else (z0 == 2, Stay) 15 16 runAltSimulation n g = do 17 rs <- liftM (filter fst) (replicateM n (montyRandSwitch g)) 18 let winBySwitch = length . filter ((== Switch) . snd) $ rs 19 winByStay = length . filter ((== Stay) . snd) $ rs 20 return (winBySwitch, winByStay) 21 22 runSimulation n g = do 23 [n0, n1] <- mapM runMontyOnSwitch [True, False] 24 putStrLn $ "proportion of wins, switching: " ++ show (n0 / fromIntegral n) 25 putStrLn $ "proportion of wins, staying: " ++ show (n1 / fromIntegral n) 26 where runMontyOnSwitch b = liftM (sum . map (\a -> if a then 1 else 0)) 27 (replicateM n (monty b g)) 28 29 main = create >>= runSimulation 10000 30