std :: mt19937需要暖机吗? [英] Does std::mt19937 require warmup?

查看:562
本文介绍了std :: mt19937需要暖机吗?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我已经读过,许多伪随机数字生成器需要许多样本,以便预热。是这样的情况下使用std :: random_device种子std :: mt19937,或者我们可以期望它在构建后准备好了吗?有问题的代码:

  #include< random> 
std :: random_device rd;
std :: mt19937 gen(rd()); Mersenne Twister是一种基于移位寄存器的pRNG(伪随机存取存储器),它是一种基于移位寄存器的寄存器。 - 随机数发生器),因此受到具有长运行0或1的不良种子,导致相对可预测的结果,直到内部状态混合足够。



获取单个值的构造函数对该种子值使用复杂函数,该函数被设计为使产生这种坏状态的可能性最小化。还有第二种方法来初始化 mt19937 ,其中通过符合SeedSequence概念的对象直接设置内部状态。






这是第二种初始化方法,您可能需要关心选择该标准包括符合SeedSequence概念的对象,称为 seed_seq seed_seq 获取任意数量的输入种子值,然后对这些值执行某些操作,以便生成适合直接设置pRNG内部状态的不同值序列。



下面是一个加载种子序列的例子,它有足够的随机数据填充整个 std :: mt19937 状态:

  std :: array< int,624& seed_data; 
std :: random_device;
std :: generate_n(seed_data.data(),seed_data.size(),std :: ref(r));
std :: seed_seq seq(std :: begin(seed_data),std :: end(seed_data));

std :: mt19937 eng(seq);

这可确保整个状态随机化。此外,每个引擎指定从seed_sequence读取多少数据,因此您可能想要读取文档以找到使用的任何引擎的信息。



虽然这里我加载指定seed_seq完全从 std :: random_device seed_seq ,使得只有几个数字不是特别随机应该工作得很好。例如:

  std :: seed_seq seq {1,2,3,4,5} 
std :: mt19937 eng(seq);

在下面的注释中,Cubbi表示 seed_seq



这里是你的'默认'种子的:

  std :: random_device r; 
std :: seed_seq seed {r(),r(),r(),r(),r()
std :: mt19937 rng(seed);


I've read that many pseudo-random number generators require many samples in ordered to be "warmed up". Is that the case when using std::random_device to seed std::mt19937, or can we expect that it's ready after construction? The code in question:

#include <random>
std::random_device rd;
std::mt19937 gen(rd());

解决方案

Mersenne Twister is a shift-register based pRNG (pseudo-random number generator) and is therefore subject to bad seeds with long runs of 0s or 1s that lead to relatively predictable results until the internal state is mixed up enough.

However the constructor which takes a single value uses a complicated function on that seed value which is designed to minimize the likelihood of producing such 'bad' states. There's a second way to initialize mt19937 where you directly set the internal state, via an object conforming to the SeedSequence concept. It's this second method of initialization where you may need to be concerned about choosing a 'good' state or doing warmup.


The standard includes an object conforming to the SeedSequence concept, called seed_seq. seed_seq takes an arbitrary number of input seed values, and then performs certain operations on these values in order to produce a sequence of different values suitable for directly setting the internal state of a pRNG.

Here's an example of loading up a seed sequence with enough random data to fill the entire std::mt19937 state:

std::array<int, 624> seed_data;
std::random_device r;
std::generate_n(seed_data.data(), seed_data.size(), std::ref(r));
std::seed_seq seq(std::begin(seed_data), std::end(seed_data));

std::mt19937 eng(seq);

This ensures that the entire state is randomized. Also, each engine specifies how much data it reads from the seed_sequence so you may want to read the docs to find that info for whatever engine you use.

Although here I load up the seed_seq entirely from std::random_device, seed_seq is specified such that just a few numbers that aren't particularly random should work well. For example:

std::seed_seq seq{1, 2, 3, 4, 5};
std::mt19937 eng(seq);

In the comments below Cubbi indicates that seed_seq works by performing a warmup sequence for you.

Here's what should be your 'default' for seeding:

std::random_device r;
std::seed_seq seed{r(), r(), r(), r(), r(), r(), r(), r()};
std::mt19937 rng(seed);

这篇关于std :: mt19937需要暖机吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆