我有以下功能,它可以实现我想要的单个呼叫:
let shuffle (arr : 'a array) =
let array = Array.copy arr
let rng = new Random()
let n = array.Length
for x in 1..n do
let i = n-x
let j = rng.Next(i+1)
let tmp = array.[i]
array.[i] <- array.[j]
array.[j] <- tmp
array
但是,对于多次调用,如下所示(x不用于任何内容),它会为每次调用产生相同的shuffle。如何让它每次都产生不同的混乱?
[for x in 1..3 do yield shuffle [|1;2;3|]]
>
val it : int [] list = [[|1; 3; 2|]; [|1; 3; 2|]; [|1; 3; 2|]]
答案 0 :(得分:5)
你想在函数之外移动随机:
let rng = new Random()
let shuffle (arr : 'a array) =
let array = Array.copy arr
let n = array.Length
for x in 1..n do
let i = n-x
let j = rng.Next(i+1)
let tmp = array.[i]
array.[i] <- array.[j]
array.[j] <- tmp
array
原因是RNG默认按时间播种,在紧密循环中没有足够的变化。将rng移到函数外部意味着它会在调用过程中持续存在。