我想在 C++ 中生成 0 到 1 之间的统一随机数,其方式不使用标准 rand()
和 srand(time(NULL))
方法。这样做的原因是,如果我在时钟的同一秒内多次运行应用程序,种子将完全相同并产生相同的输出。
我不想依赖提升或操作系统/编译器细节。可以假定为 x86。
似乎另一种方法是使用 TR1(我没有 C++11)并以某种方式使用 /dev/random
进行播种?
现在我有这个,但它仍然使用 time(NULL)
作为种子,在 1 秒内运行将无法正常工作:
#include <iostream>
#include <tr1/random>
int main()
{
std::tr1::mt19937 eng;
eng.seed(time(NULL));
std::tr1::uniform_int<int> unif(1, RAND_MAX);
int u = unif(eng);
std::cout << (float)u/RAND_MAX << std::endl;
}
最佳答案
应 OP 要求发布:
这在某种程度上仍然是特定于编译器的,但仍然适用于几乎所有以 x86 为目标的编译器:
#ifdef _WIN32
// Windows
#define rdtsc __rdtsc
#else
// For everything else
unsigned long long rdtsc(){
unsigned int lo,hi;
__asm__ __volatile__ ("rdtsc" : "=a" (lo), "=d" (hi));
return ((unsigned long long)hi << 32) | lo;
}
#endif
int main()
{
std::tr1::mt19937 eng;
eng.seed( rdtsc() ); // Seed with rdtsc.
std::tr1::uniform_int<int> unif(1, RAND_MAX);
int u = unif(eng);
std::cout << (float)u/RAND_MAX << std::endl;
}
这里的想法是使用 rdtsc
循环计数器为您的随机数生成器提供种子。
之所以可行,是因为 rdtsc
循环计数器以与 CPU 频率大致(通常相同)的速度迭代。因此,两次调用它返回相同值的机会非常小 - 因此,使其成为 RNG 的极好种子。
关于c++ - 使用 TR1/dev/random 在 C++ 中生成随机数(弹性到 <1 秒运行),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8661231/