为什么“使用sleep()”会使同一代码的结果有所不同?

时间:2019-05-21 15:51:35

标签: c++

我编写了一个程序,该程序创建一个包含随机字符串的字符串数组,rand_str()的长度为20个字符串。当我使用sleep()时,结果正是我想要的。但是,我认为sleep()不应该出现在我的代码中。删除sleep(),创建的随机字符串完全不同。我对此很困惑。有人可以帮忙解释为什么会这样吗?

#include <iostream>
#include <string.h>
#include <random>
#include <ctime>
#include <cstdlib>
#include <windows.h>
#include <stdlib.h>
#include <array>
#define show(w) for(auto val:w){cout<<val<< " ";}cout<<endl;
using namespace std;

char *rand_str(char *str,const int len);

int main(){
    const int len = 10;
    char *a[len];
    string c[len];
    array<string,len> ar;char b[len][21];
    for (int i = 0; i < len; ++i) {
        ar[i] = rand_str(b[i], 21);
        fflush(stdin);
//      Sleep(1000);
    }
    show(ar);
    return 0;
}
char *rand_str(char *str,const int len){
    srand(time(NULL));
    int i;
    for(i=0;i<len;++i)
    {
        switch((rand()%3))
        {
            case 1:
                str[i]='A'+rand()%26;
                break;
            case 2:
                str[i]='a'+rand()%26;
                break;
            default:
                str[i]='0'+rand()%10;
                break;
        }
    }
    str[len - 1]='\0';
    return str;
}

不使用sleep():

enter image description here

使用sleep():

enter image description here

4 个答案:

答案 0 :(得分:3)

您编写的程序执行得足够快,以至于rand_str的每个循环极有可能在一秒钟的时间内发生。这很重要,因为生成字符串的方法涉及对time的调用,因为time返回一个time_t对象,该对象在C标准中指定为:

  

未指定time_t中的日历时间编码,但是大多数系统符合POSIX规范,并返回一个整数类型的值,该值保存了自大纪元以来的秒数。其中time_t是32位有符号整数的实现(许多历史实现)在2038年失败。

     

time C++ Reference

因此,如果整个程序在不到一秒的时间内执行,则在该范围内对time的每次调用都将返回相同的值,并为您的随机数播种相同的值,并在每个循环中产生相同的输出。相反,Sleep持续1000毫秒(1秒)时,您几乎可以保证每次执行都将具有不同的种子,因此输出也不同。

通常,在程序开始时,只应给随机数播种一次。另外,您应该考虑使用<random>库,因为它包含了生成随机数更好的机制。

答案 1 :(得分:2)

rand_str最有可能与时间相关。您提出的种子的 seed 设置为srand(time(NULL));,所以确实如此。

Sleep(1000)(至少睡眠1000个单位的 时间)足以更改结果。

删除睡眠调用和程序执行速度足够快,以至于无法观察到rand_str的时间依赖性。

答案 2 :(得分:1)

您的rand_str函数在每次调用时重新植入PRNG ,并使用以秒为单位的当前时间。然后,它将按该顺序拉出“第一个”数字并返回它。

这意味着对于不同时间的函数调用,您只会获得不同的伪随机序列。如果在同一秒内进行多个函数调用,则使用相同的种子继续进行重新播种,这将导致相同的序列,并且相同序列中的第一个数字始终是相同的数字。这就是为什么睡眠有所作为:它改变了种子。

您应该先only seed once, at the start of your program,然后根据需要use the resulting sequence

顺便说一下,整个方法论已经过时了。从C ++ 11开始,we do random numbers like this

答案 3 :(得分:-1)

这很可能是由于计算机无法产生真正的随机数。 因此,存在称为seed的概念。伪随机数生成最常见的seed是时间。 让您的程序稍等一下,将使其以其他种子运行随机生成器。