mt19937和uniform_real_distribution

use*_*488 5 c++ boost prng mersenne-twister

我试图找到一种有效的方法来实现统一(0,1)分布.由于我必须生成大量样本,所以选择mt19937作为引擎.我正在使用boost库中的版本.我的问题是:使用引擎本身的输出与使用uniform_real_distribution之间的区别是什么?

选项1

std::random_device rd;
boost::mt19937 gen(rd());
boost::random::uniform_real_distribution<double> urand(0, 1);

for ( int i = 0; i < 1E8; i++ ) {
    u = urand(gen);
}
Run Code Online (Sandbox Code Playgroud)

选项#2

std::random_device rd;
boost::mt19937 gen(rd());

for ( int i = 0; i < 1E8; i++ ) {
    u = (double) gen()/gen.max();
}
Run Code Online (Sandbox Code Playgroud)

从我的测试来看,在运行时方面,选项#2比选项#1好得多.我是否应该选择#2选项#1?

sh1*_*sh1 1

我不知道 的底层实现urand(),但使用除法的结果可能会在低阶位中产生偏差作为量化效应。如果gen.max()不大,则“低位位”可能是结果的很多位或大部分位。

性能差异可能来自于生成正确分布的随机数。如果double对于您的需求来说过于精确,那么也许使用float可能会使其运行更有效。