一、需求
我需要生成10组随机数,每组随机数的维度是5*5,要求每组随机数是不同的,但是又要求每次运行程序生成的随机数是可重复的。
最简单的办法如下:
program test_random_number
!!!!!!可以不设置种子,效果相同。
REAL :: r(5,5)
do i=1,10
call random_number(r)
write(*,*)r
print*,'-------------------------------------'
enddo
end program
程序运行后,输出结果为:
3.9208680E-07 2.5480442E-02 0.3525161 0.6669145 0.9630555
0.8382882 0.3353550 0.9153272 0.7958636 0.8326931
0.3450427 0.8711839 8.9918353E-02 0.8882838 0.7009789
0.7345526 0.3001758 4.9717721E-02 0.9081894 9.7658597E-02
4.0313378E-02 8.5024789E-02 0.5588210 0.9264517 7.5640768E-02
-------------------------------------
0.9117896 9.1822170E-02 0.6377664 0.8522921 0.1210777
0.9945745 0.7782503 1.9665021E-02 0.1698636 0.9947433
0.7536924 0.2179738 0.6592925 0.5390184 0.4800633
0.8392264 2.5420204E-02 0.9893829 0.5857707 0.7670679
0.4448168 0.7095050 0.7945260 0.4387013 0.2087533
-------------------------------------
0.7311121 0.6657310 0.7220742 0.2114710 0.3082515
0.2629889 0.7522959 0.5497946 0.6367239 0.6310104
0.4947841 0.4706950 0.1225150 0.5348967 0.1941571
0.9679053 0.5892302 1.7623320E-02 0.3143427 0.5533030
0.6762834 1.6883278E-02 0.2656559 0.4608800 0.8374500
-------------------------------------
每次运行的输出结果都是相同的。
我认为上述结果是因为,fortran默认的有一个随机种子,所以不设置直接调用random_number就可以了。
如果想更灵活一点,不使用系统默认的随机种子,可以手动设置一个随机种子,方法如下:
program test_random_number
!!!!!!设置一个种子,每次运行都会生成相同的随机数,但是每个循环里生成的随机数是不同的
!!!!!!和不设置种子的效果相同。
REAL :: r(5,5)
integer :: n(1)
integer,allocatable :: seed(:)
n=123456
call random_seed(put=n)
print*,'-------------------------------------'
do i=1,10
call random_number(r)
write(*,*)r
print*,'-------------------------------------'
enddo
end program
n就是我们设置的种子,put是random_seed子程序的输入参数(intent(in)),n必须是一个数组。关于random_seed的另外两个参数,size和get,都是输出参数,笔者自己没有弄的很明白,也没有使用的需求,欢迎大佬在评论区赐教。个人觉得这篇说的还不错:fortran随机数
此时的输出结果如下:
0.3003711 6.1110102E-02 3.7764840E-02 0.2076357 0.3833852
0.9097154 0.4229082 0.2671735 0.5746257 0.2194885
0.5764998 0.3967984 2.7026536E-02 0.3349927 0.3099868
0.5780981 0.9329451 0.6820918 0.7257171 0.6534119
0.9531794 0.5080327 0.8002245 0.4509397 0.9372804
-------------------------------------
0.5612365 6.1461501E-02 0.7858571 0.5554050 0.4812418
0.6018271 0.3862819 0.7944903 3.1226246E-02 0.5575908
0.5348483 0.3856399 0.6524287 0.8872858 5.1918231E-02
3.9682582E-02 7.7522576E-02 0.8136503 0.8178805 0.4109471
0.6253451 0.3680272 0.9016623 0.3865243 0.3946394
-------------------------------------
0.7769522 0.9103879 0.4235442 0.8339527 0.2920198
0.7666448 4.0062513E-02 0.2423317 0.8170069 0.4758632
0.4376644 0.8842280 0.2314132 0.9875546 0.8472762
0.8744933 0.8001316 2.4753891E-02 0.6369917 3.1933367E-02
0.5903373 0.9698811 0.5209839 0.1557297 0.5503737
-------------------------------------
可以看到,和不设置随机种子时生成的随机数不同,每次运行结果也都是一样的,改变n的赋值则可以得到另外的随机数。
另外,如果想使每次运行程序得到的随机数都是不同的,(这样做程序运行结果将不可重复),可以这样写:
program test_random_number
REAL :: r(5,5)
call random_seed()
do i=1,10
call random_number(r)
write(*,*)r
print*,'-------------------------------------'
enddo
end program
也就是调用random_seed(),但是不传入参数,每次运行时会根据系统时间设置随机种子,更具体原理在刚才的链接中有提到。
fortran设置随机种子和生成随机数,以上满足了笔者的需求,如果有更高端的用法,欢迎评论区留言。