C ++问题,使用Code :: Blocks。 我正在尝试运行此代码来测试伪随机函数
#include <iostream>
#include <cstdlib>
#include <ctime>
using namespace std;
int main()
{
int count = 0;
while (count < 10){
srand(time(NULL));
cout << rand() << ' ';
cout << (time( NULL )) << " \n";
count++;
}
return 0;
}
此输出为10条相等的线。这不是真正的问题,因为这里的种子是相同的,所以结果应该是相同的。问题是如果我再次运行这个程序,它会产生10个非常相似的行,不仅在time()输出上有很小的变化,而且在rand输出上也是如此。
srand(time(NULL))给出了非常相似的答案,这些答案基本上是相同的返回值,只是稍大一些。
(第一次运行时返回9631,然后是第二次运行时返回9656)。
我的问题是,这是预期的行为吗?如何在第一次运行时获得更多不同的结果,如38,在第二次运行时获得671?
答案 0 :(得分:2)
这里有很多误解......预计两个time(NULL)
次呼叫之间的差异很小。毕竟,时间的移动速度非常快。下一个问题是rand()
返回(伪)随机值(质量不同):在这种情况下,随机意味着您可能会重复几次33
,只要它不可预测。话虽如此,rand()
依赖于实现,很可能你的实现使用类似LCG的东西,它不会产生良好的统一随机值。唯一的解决方法是切换到不同的rng。由于这被标记为C ++,您可能需要查看C ++ 11s随机标题并使用类似mersenne twister实现的内容,这是一个很好的伪随机数生成器,它可以生成质量高,分布均匀的随机数。 / p>
答案 1 :(得分:1)
不同执行之间的差异可能是time
变化的微小差异。对于不同的C运行时,rand
的结果可能不同,但这是Visual Studio 10中rand
的实现。
int __cdecl rand ()
{
_ptiddata ptd = _getptd();
return( ((ptd->_holdrand = ptd->_holdrand * 214013L
+ 2531011L) >> 16) & 0x7fff );
}
holdrand
存储种子以开始使用。这是linear congruential generator,通常不会产生高质量的随机性。它每次都会丢掉很多状态但没有帮助。
答案 2 :(得分:0)
要使用几乎相同的种子(时间)创建一个随机数,您可以添加一个静态变量,使rand()
即使使用相同的参数也会表现不同;或者,您可以在同一时间更改参数。例如:
int t=0;
...
rand(t=(t*7)^time(NULL));