C++ 跨平台的一致伪随机数

C++ 跨平台的一致伪随机数,c++,c,random,C++,C,Random,我正在寻找一种生成伪随机数序列的方法,该序列将在任何平台上为给定种子生成相同的序列结果。我假设rand()/srand()是不一致的(这个假设很容易出错)。最简单的方法是自己编写一个随机数生成器,但是使用一个为不同平台发布的库并保证给出相同的结果也可以工作 我怀疑rand()/srand()是否一致,但我不知道。类似于a的东西是确定性的。谷歌搜索的一个快速关键词说: 使用同一种子进行两次不同的初始化,指示伪随机生成器为两种情况下的后续rand调用生成相同的连续结果 但问题依然存在。我假设上述规范

我正在寻找一种生成伪随机数序列的方法,该序列将在任何平台上为给定种子生成相同的序列结果。我假设
rand()
/
srand()
是不一致的(这个假设很容易出错)。

最简单的方法是自己编写一个随机数生成器,但是使用一个为不同平台发布的库并保证给出相同的结果也可以工作

我怀疑rand()/srand()是否一致,但我不知道。

类似于a的东西是确定性的。

谷歌搜索的一个快速关键词说:

使用同一种子进行两次不同的初始化,指示伪随机生成器为两种情况下的后续rand调用生成相同的连续结果


但问题依然存在。我假设上述规范仅适用于同一流程中的RNG。它很可能没有指定任何关于跨平台或跨编译器的内容。您最好的选择可能是找到一个可用于所有所需平台的库。然后,如果使用相同的值进行种子设定,则返回相同的数字序列,这应该是相当安全的。

Knuth对《计算机编程艺术》第3.6节中描述的伪随机数生成器进行了改进。

。以下是从页面中提取的示例,默认使用
Mersenne捻线机
引擎和
Normal
分布:

#include <iostream>
#include <iomanip>
#include <string>
#include <map>
#include <random>

int main()
{
    std::random_device rd;

    //
    // Engines 
    //
    std::mt19937 e2(rd());
    //std::knuth_b e2(rd());
    //std::default_random_engine e2(rd()) ;

    //
    // Distribtuions
    //
    std::normal_distribution<> dist(2, 2);
    //std::student_t_distribution<> dist(5);
    //std::poisson_distribution<> dist(2);
    //std::extreme_value_distribution<> dist(0,2);

    std::map<int, int> hist;
    for (int n = 0; n < 10000; ++n) {
        ++hist[std::round(dist(e2))];
    }

    for (auto p : hist) {
        std::cout << std::fixed << std::setprecision(1) << std::setw(2)
                  << p.first << ' ' << std::string(p.second/200, '*') << '\n';
    }
}
#包括
#包括
#包括
#包括
#包括
int main()
{
std::随机_装置rd;
//
//引擎
//
std::mt19937 e2(rd());
//std::knuth_b e2(rd());
//std::默认的随机引擎e2(rd());
//
//分布
//
标准:正态分布区(2,2);
//学生分布区(5);
//标准:泊松分布区(2);
//标准:极值分布距离(0,2);
地图历史;
对于(int n=0;n<10000;++n){
++hist[std::round(dist(e2))];
}
用于(自动p:hist){

std::cout我一直在为此开发一个库。它应该是跨平台的,我还瞄准多种语言。目前它支持C和(两种语言生成的数字相同)我计划在C++中实现同样的生成器,在Boost和C++ 11随机API之后。

我相信这是指他对代码的任何具体实现。
,不提供任何交叉编译器或跨平台保证。此外,内置PRNG会使各种不需要的属性面临风险。请使用一个库,该库中的PRNG适合您的需要。如果您希望避免Boost,可以使用的原始实现,它是用C编写的。近年来MT group添加了一些可以使用SIMD、OpenCL和CUDA的附加端口。请参阅我的C++11随机生成器问答。C++11 mt19937在所有平台上提供一致的结果,但标准发行版没有,因此我创建了自己的发行版:不需要C++11标准指定的发行版即使使用相同的代码,在给定相同种子的情况下也能产生可重复的结果。更不用说使用不同的库,比如libc++和libstdc++。请参阅我的C++11随机生成器问答。C++11 mt19937在所有平台上都能提供一致的结果,但标准发行版不能,因此我创建了自己的发行版:请参阅mC++11随机生成器的y问答。C++11 mt19937可在所有平台上提供一致的结果,但标准分布不一致,因此我创建了自己的分布:如果您选择使用线性同余生成器,则非常有用。特别是您可以使用ISO中建议的
rand
的C实现/IEC 9899。在我的测试中,当
无符号长
使用32位(最小)或64位时,它给出了相同的结果。