c++std::normal_distribution在从文件恢复时给出不一致的随机数

c++ std::normal_distribution gives inconsistent random numbers when restoring from file

本文关键字:随机数 恢复 不一致 文件 normal distribution c++std      更新时间:2023-10-16

我正在编写一个蒙特卡罗模拟并实现了检查点。我想获得完全相同的结果,无论我是否从检查点重新启动模拟或继续超过它。然而,我在std::normal_distribution:中遇到了一些奇怪的行为

我使用std::mt19937 rng;作为RNG,并将其种子设定为一个固定的数字。我通过CCD_ 3和CCD_。然后,我将rng的状态写入ofstream os:

os << rng << endl;
os << <some other stuff>...

紧接着,我又画了几个数字:

os << uniform(rng) << endl;
os << uniform(rng) << endl;
os << uniform(rng) << endl;
os << normal(rng) << endl;
os << normal(rng) << endl;
os << normal(rng) << endl;
os << uniform(rng) << endl;
os << uniform(rng) << endl;
os << uniform(rng) << endl;

我得到以下输出:

0.727133
0.215537
0.516879
-2.12532
0.314652
1.78136
0.511111
0.83119
0.637067

然而,如果我从检查点重新启动,即从ifstream is:初始化生成器

is >> rng;
is >> <some other stuff>...

并画出相同的9个随机数(3个均匀,3个正常,3个均匀),我得到:

0.727133
0.215537
0.516879
0.314652
1.78136
1.28201
0.637067
0.298175
0.802607

你看,统一的数字是相同的,直到画出一个正常的数字,之后rng的状态不同。gdb的介入证实了这一点。

查看0.637067在两个输出中的位置。你会注意到,正态分布在恢复时必须从rng中提取比未恢复时更多的数字。这是因为当你检查点的时候它有熵。

您必须保存或重置normal的状态。我建议在normal上调用reset作为检查点过程的一部分。