Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/fortran/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Random Fortran 90的随机数生成器是否可以用于蒙特卡罗积分?_Random_Fortran_Integration_Montecarlo - Fatal编程技术网

Random Fortran 90的随机数生成器是否可以用于蒙特卡罗积分?

Random Fortran 90的随机数生成器是否可以用于蒙特卡罗积分?,random,fortran,integration,montecarlo,Random,Fortran,Integration,Montecarlo,我用Fortran 90编写了一个简短的蒙特卡罗积分算法来计算积分。我曾经比较过使用内在随机数生成器和Fortran90第2卷的数值公式中给出的随机数生成器方法ran1求解某个参数的积分所得到的结果 运行相同的算法两次,一次调用内在的random_seed(),然后始终调用random_number(),一次调用数字配方书中提供的ran1()方法,我得到的结果基本上是相同的形状,但内在结果是与ran1结果相反的连续曲线。在这两种情况下,对于参数值q,我使用随机参数调用函数10000次,将其相加,

我用Fortran 90编写了一个简短的蒙特卡罗积分算法来计算积分。我曾经比较过使用内在随机数生成器和Fortran90第2卷的数值公式中给出的随机数生成器方法ran1求解某个参数的积分所得到的结果

运行相同的算法两次,一次调用内在的random_seed(),然后始终调用random_number(),一次调用数字配方书中提供的ran1()方法,我得到的结果基本上是相同的形状,但内在结果是与ran1结果相反的连续曲线。在这两种情况下,对于参数值q,我使用随机参数调用函数10000次,将其相加,然后继续下一个q值,并调用函数10000次,以此类推

可在此处找到结果的比较图像:

如果我增加调用数,两条曲线都会收敛。但我想知道:为什么内在随机数生成器会产生这种平滑度?是否仍普遍建议使用它,或是否有其他更建议的RNG?我假设连续的结果是内在数生成器“较少”随机性的结果


(我省略了源代码,因为我认为它没有太多的输入。如果有人关心,我可以稍后提交。)

标准Fortran中的伪随机生成器的质量没有保证。如果您关心密码学或对随机数敏感的科学(蒙特卡罗)的某些特定实现质量,那么您应该使用一些您可以控制的库

你可以研究一下你的编译器手册,看看它是如何描述随机数生成器的,但是每个编译器都可以实现一个完全不同的算法来生成随机数

在数值数学界,一些人并不喜欢数字食谱

这个网站不是为软件推荐而建的,但是这篇文章(roygvib在评论中给出的链接):是一篇很好的评论,有好算法和坏算法的例子,如何测试它们的方法,如何生成任意数分布,以及C语言中两个示例库的调用示例(其中一个也可以从Fortran调用)


我个人使用这个并行PRNG,但我没有测试质量,我个人只需要速度。但这不是一个软件推荐网站。

我同意弗拉达米尔F。但是

< >为了帮助您更好地寻找随机数,考虑最近的C++添加。Mersenne twister和其他很多人都在那里。这是一个经过深思熟虑的系统。我认为有两种方法可以测试这些序列:

  • 从FORTRAN向一个小的C++实用程序发出一个系统调用,这些程序为您或
  • 生成一组它们
  • 通过ISO_C_绑定将随机数生成器绑定到Fortran
我更喜欢第二种,因为绑定有点棘手,所以我准备了一个示例。这些文件是:

  • cxx11_rand.h和cxx11_rand.cpp,它们定义对随机数生成器的调用
  • 在C函数中调用C++函数的C.RAND.CPP
  • f_rand_M.f90,它将C函数绑定到Fortran
  • f_main.f90,它使用模块函数在[0,1]中生成10个随机数
  • cxx11_rand.h
    \ifndef CXX11\u RAND\u H
    #定义CXX11和
    无效cxx11_init();
    双cxx11_rand();
    #恩迪夫
    
    cxx11_rand.cpp
    #包括
    #包括
    #包括
    #包括
    #包括
    #包括
    #包括
    #包括
    #包括
    #包括“cxx11_rand.h”
    静态标准::唯一的ptr距离;
    静态标准::唯一的ptr工程;
    无效cxx11_init(){
    eng=std::unique_ptr(新std::mt19937_64(std::random_device{}());
    dist=std::unique_ptr(新std::uniform_real_distribution(0.0,1.0));
    }
    双cxx11_rand(){
    报税表(*地区)(*英文);
    }
    
    c_rand.cpp
    #包括“cxx11_rand.h”
    #ifdef_uucplusplus
    外部“C”{
    #恩迪夫
    void c_init(){
    cxx11_init();
    }
    双c_rand(){
    返回cxx11_rand();
    }
    #ifdef_uucplusplus
    }
    #恩迪夫
    
    f_rand_M.f90
    模块f_和M
    隐式无
    !定义到C函数的fortran接口绑定
    接口
    子例程fi_init()绑定(C,name=“C_init”)
    结束子程序
    实数(C_DOUBLE)函数fi_rand()绑定(C,name=“C_rand”)
    使用ISO_C_绑定,仅限:C_DOUBLE
    端函数
    端接口
    包含
    子程序f_init()
    调用fi_init()
    结束子程序
    实(C_-DOUBLE)函数f_-rand()
    使用ISO_C_绑定,仅限:C_DOUBLE
    f_rand=f_rand()
    端函数
    端模块
    
    f_main.f90 您可以使用以下GNU命令编译/链接

    echo "compiling objects"
    g++ -c --std=c++11 cxx11_rand.cpp c_rand.cpp
    gfortran -c f_rand_M.f90
    
    echo "building & executing fortran main"
    gfortran f_main.f90 f_rand_M.o c_rand.o cxx11_rand.o -lstdc++ -o f_main.exe
    ./f_main.exe
    
    您的输出应该是这样的(当然有不同的随机数——这里的种子是从“熵源”中选择的,例如墙时间)


    我在Mac上使用GCC 4.9进行测试。

    PRNG在您进行MC时是一个不好的选择,无论使用哪种编程语言。对于MC模拟,最好使用诸如或之类的服务。第47项中的书清楚地显示了一个有问题的PRNG示例。使用PRNG,您永远无法确定您对其内部imp是否满意实现。

    使用的特定随机数生成器取决于编译器。可能有文档记录,可能没有。可能会有更改。为了获得高质量的工作,我会使用其他地方的库/源代码。包含Mersenne Twister的Fortran实现的网页:。我已使用并验证了原始实现更新。此版本对多线程程序非常有用。

    所有Fortran问题都使用标记。如果需要,请添加版本标记以区分。顺便说一句,可能不在这里,因为相同的RNG在更高版本中,95、2003、2008、2015…啊,好的,谢谢。我还没有学习过更高版本的
    echo "compiling objects"
    g++ -c --std=c++11 cxx11_rand.cpp c_rand.cpp
    gfortran -c f_rand_M.f90
    
    echo "building & executing fortran main"
    gfortran f_main.f90 f_rand_M.o c_rand.o cxx11_rand.o -lstdc++ -o f_main.exe
    ./f_main.exe
    
    compiling objects
    building & executing fortran main
      0.47439556226575341
      0.11177335018127127
      0.10417488557661241
      0.77378163596792404
      0.20780793755332663
      0.27951447624366532
      0.66920698086955666
      0.80676663600103105
      0.98028384008440417
      0.88893587108730432