読者です 読者をやめる 読者になる 読者になる

はわわーっ

はわわわわっ

haskell で乱数

乱数を使ってみる。とりあえず、System.Random をインポート。

import System.Random

乱数は random と getStdRandom を使えばよい。型はそれぞれ

random :: RandomGen g => g -> (a, g)
getStdRandom :: (StdGen -> (a, StdGen)) -> IO a

となっている。例えば Int 型の乱数が欲しければ

getRandomInt :: IO Int
getRandomInt = getStdRandom random

main :: IO()
main = do
  rand <- getRandomInt
  print rand

みたいにやればいい。わざわざ関数を作る必要がないときは

main :: IO()
main = do
  rand <- (getStdRandom random :: IO Int)
  print rand

こんな感じ。
範囲を指定してその範囲内の乱数が欲しい時は random の代わりに randomR を使う。

randomR :: RandomGen g => (a, a) -> g -> (a, g)
main :: IO()
main = do
  rand <- (getStdRandom $ randomR (0,1) :: IO Double)
  print rand

これで 0 から1 の間の乱数ができる。
乱数のリストが欲しい時は

import Control.Monad (replicateM)

main :: IO()
main = do
  rands <- replicateM 10 $ (getStdRandom $ randomR (0,99) :: IO Int)
  print rands

みたいに replicateM を使えばよい。ただ、これと同じような感じで

import Control.Monad (sequence)

main :: IO()
main = do
  rands <- sequence $ repeat $ (getStdRandom $ randomR (0,99) :: IO Int)
  print $ take 10 rands

ってやると無限リストが作れるかと思ったけど、これはできなかった(?)。よくわかってない。

無限リストは getStdGen と randoms か randomRs を使うとできる。

getStdGen :: IO StdGen
randoms :: RandomGen g => g -> [a]
randomRs :: RandomGen g => (a, a) -> g -> [a]
main :: IO()
main = do
  gen <- getStdGen
  print $ take 10 $ (randomRs (0,99) gen :: [Int])