【发布时间】:2017-03-04 06:44:57
【问题描述】:
以下算法生成一个不重复的随机数数组(示例是用 Fortran 95 编写的):
program test
implicit none
real :: x
integer :: i, aux
integer, dimension(100) :: y = 0
do i=2,100
call RANDOM_NUMBER(x)
aux = int(3 * x) + 1 ! random number: 1, 2 or 3
aux = aux + y(i-1) ! adding previous selected number
y(i) = MOD(aux,4) ! mod 4 gives the final result: 0, 1, 2 or 3
print*, y(i)
enddo
end program test
在另一个论坛上,一位成员提出了该算法,以解决如何使用常规随机数生成器和每个循环固定数量的操作(例如,当随机值循环与前一个相同,不会给出每个循环的恒定操作数)。
他的算法似乎运行良好,结果是均匀分布的,并且在输出中 any 的任何子字符串中都没有明显的模式(我搜索了大小为 2 到 5 的子字符串,并且所有行为都符合预期)。但是这个解决方案让我感到困惑的是,随机数生成器只输出三个可能的数字(0、1 或 2),而整个算法却输出了四个可能的结果(0、1、2 或 3)。这怎么可能?我认为可以映射 PRNG 的结果,但不能映射它(例如,如果 PRNG 产生 0 到 7 之间的数字,它们可以映射为 0-3 => 0 和 4-7 =>1,但是只产生 0 和 1 的 PRNG 不能在同一循环中产生 0-7 之间的结果 - 因为显然可以将三个结果分组以映射 000 => 0, 001 => 1, .. . 111 => 7).
编辑:这是相同的算法,但用伪代码编写,因为这个问题与 Fortran 或任何编程语言无关
x ← 0
do
aux ← random number between 1 and 3
aux ← aux + x
x ← aux MOD 4
print x
enddo
【问题讨论】: