rand()函数与srand()函数以及随机数种子详解

这篇具有很好参考价值的文章主要介绍了rand()函数与srand()函数以及随机数种子详解。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

引言

初学者大部分对这两个函数的意义都不甚了解,以及不明白为什么需要srand()函数来播种,这里会对两函数的意义进行解释,让大家明白两函数搭配的作用,并对伪随机数以及真随机数进行讲解,最后会对随机数生成的原理进行一些探讨,希望对大家的学习理解有所帮助

rand()函数

格式:

int rand(void); //void表示不需要参数

当没有参数时rand() 会随机生成一个位于 0 ~ RAND_MAX 之间的整数。

RAND_MAX 是 <stdlib.h> 头文件中的一个宏,它用来指明 rand() 所能返回的随机数的最大值。C语言标准并没有规定 RAND_MAX 的具体数值,只是规定它的值至少为 32767。在实际编程中,我们也不需要知道 RAND_MAX 的具体值,把它当做一个很大的数来对待即可。

用法(求余):

如下取值范围为j ~ i :

rand() % (i - j + 1+ j; //i表示随机数生成的最大值,j表示随机数生成的最小值

实例:

#include <stdio.h>
#include <stdlib.h>

int main()
{
    printf("%d\n",rand());
    return 0;
}

运行后会发现每次结果都是相同的,原因是rand()函数生成的是伪随机数(即通过算法生成,是正态分布的,并不是真正的随机),而非真随机数,那么接下来就讲讲随机数

随机数

首先讲讲什么叫真随机数和伪随机数,按照定义来讲(WIKI百科)

1.真随机数:
真正的随机数是使用物理现象产生的:比如掷钱币、骰子、转轮、使用电子元件的噪音、核裂变等等。 这样的随机数生成器叫做物理性随机数生成器,它们的缺点是技术要求比较高。 在实际应用中往往使用伪随机数就足够了。 这些数列是“似乎”随机的数,实际上它们是通过一个固定的、可以重复的计算方法产生的。

2.伪随机数:
伪随机数是使用一个确定性的算法计算出来的似乎是随机的数序,因此伪随机数实际上并不随机。在计算伪随机数时假如使用的开始值不变的话,那么伪随机数的数序也不变。伪随机数的随机性可以用它的统计特性来衡量,其主要特征是每个数出现的可能性和它出现时与数序中其它数的关系。伪随机数的优点是它的计算比较简单,而且只使用少数数值很难推算出计算它的算法。一般人们使用一个假的随机数,比如电脑上的时间作为计算伪随机数的开始值。

从这里的定义我们可以知道,计算机生成的伪随机数其实是有规律可循的,并不是完全的随机,只不过它的循环周期可能比较长罢了

srand()函数

通过上面对随机数的讲解,相信大家也可以明白,仅仅是通过rand()函数,每次计算机生成的数值都是固定的,那么我们便需要想办法让rand()函数每次生成的数值是伪随机的,这样每次生成的值才不会重复,于是便需要用到srand()函数

用法:

void srand (unsigned int seed);

通过srand()函数来初始化随机种子,这个种子会对应一个随机数,如果使用相同的种子后面的 rand() 函数会出现一样的随机数,如: srand(1); 所以我们通常会使用time()函数来返回自 1970 年 1 月 1 日 到现在当前的时间,而我们当前的时间又是每秒都在变动的,所以由时间播种生成了伪随机数

实例:

#include <stdio.h>
#include <stdlib.h>
#include <time.h>

int main()
{
	srand((unsigned)time(NULL));
    printf("%d\n",rand());
    return 0;
}

执行后发现每次生成的值不再重复了

拓展思考

相信细心的朋友也考虑到了一个问题,既然通过time()函数得到的时间是根据当前时间的来的,那么如果当前时间没有发生变化的话岂不是得到的是相同的值?

这里通过for循环来进行演示

#include <stdio.h>
#include <stdlib.h>
#include <time.h>

int main()
{
	int i;
	
	for(i = 0; i < 10; i++)
	{
		srand((unsigned)time(NULL));
    	printf("%d\n",rand());
    }
    return 0;
}

这里我们将srand()函数放在for循环语句内,而for循环单次循环的时间是远小于1s的,那么srand()函数内的种子便没有发生变化,相同的种子执行结束后每次得出的结果自然是相同的,而如果将srand()函数放到for语句之外,每次生成的结果又不重复了,这样我们就既能输出一组随机数,又能避免重复了

别急还没完,到这里相信有人和我一样又考虑到,按道理来说实例这点程序,放到外面难道就会执行时间小于1s?然后导致播种每次都能是不同种子结果才会不同么?

仔细思考后以为不然,个人认为rand()这个函数在播种以后其实是生成了一个伪随机数序列,而连续调用这一种子,第一次输出的是序列中第一个值,第二次输出的是序列中第二个值,这样依次下去输出,所以在for循环外时可以得到不同的随机值;但在for循环内的话由于执行速度太快小于1s,相当于每次都连续播种了同一个种子,这样每次只能输出序列的第一个值,所以结果当然是几个同样的值

实例验证:

#include <stdio.h>
#include <stdlib.h>
#include <time.h>

int main()
{
        int i;
        time_t begin,end;
        
		begin = time(NULL);
		
		//在循环体外部初始化种子
        srand((unsigned)time(NULL));
        for(i = 0; i < 10; i++)
        {
                printf("%d ",rand());
        }

        putchar('\n');

		//在循环体内部初始化种子
        for(i = 0; i < 10; i++)
        {
                srand((unsigned)time(NULL));
                printf("%d ",rand());
        }

        putchar('\n');

		//未初始化种子
        for(i = 0; i < 9; i++)
        {
                printf("%d ",rand());
        }

        putchar('\n');

		end = time(NULL);

		printf("程序执行所花费的时间为:%ld\n",end - begin);

        return 0;
}

输出结果如图:

首先我们可以看到计算程序执行所花费的时间为0,说明程序执行时间小于1s,然后再对比程序的执行结果,循环内得出的结果和循环外结果均与序列的第一个值相同,而第三个循环体未初始化种子,那么种子延续上面初始化的种子,输出的9个值与循环体外结果序列的后9个值依次相同,猜想的原理得到验证

rand srand,C语言,c语言,开发语言文章来源地址https://www.toymoban.com/news/detail-824798.html

到了这里,关于rand()函数与srand()函数以及随机数种子详解的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • Unity如何生成随机数(设置种子)

    我们可以使用Random类来生成一些随机数 Random类是用于生成随机数的类之一。它可以用于生成不同类型的随机数,如整数、浮点数和向量。 我们可以使用Random.Range来生成指定范围内的随机整数或浮点数。下面举两个例子: 运行结果如下所示: 使用Random.insideUnitCircle来获取一个

    2024年02月04日
    浏览(40)
  • 【LINUX相关】生成随机数(srand、/dev/random 和 /dev/urandom )

    在一个循环中,生成多组随机值,发现最终的结果都一样,结果是调用的函数如下,在函数中设置了随机种子,且是以秒为单位,那么在一秒类,由于都是用一个种子,srand又是伪随机,所以最终生成的都是同一组随机字符。 2.1 修改种子 (1)将 srand(time(NULL)); 放到循环外面

    2024年02月12日
    浏览(47)
  • 基于FPGA的LFSR16位伪随机数产生算法实现,可以配置不同的随机数种子和改生成多项式,包含testbench

    目录 1.算法仿真效果 2.算法涉及理论知识概要 3.Verilog核心程序 4.完整算法代码文件 vivado2019.2仿真结果如下:           LFSR(线性反馈移位寄存器)提供了一种在微控制器上快速生成非序列数字列表的简单方法。生成伪随机数只需要右移操作和 XOR 操作。LFSR 完全由其多项式

    2024年02月11日
    浏览(45)
  • 【机器学习】scikit-learn机器学习中随机数种子的应用与重现

    随机数种子是为了能重现某一次实验生成的随机数而设立的,相同的随机数种子下,生成的随机数序列一样 一、随机数种子基础应用 在python中简单运用随机数种子 结果如下 可以看到out[6]之前加载了随机数种子1之后可以重现第一次随机数的生成结果 二、随机数种子在scikit

    2024年02月01日
    浏览(50)
  • mysql随机数函数

    declare@iint select@i=count(*)fromA while@i0 begin UpdateAsetB=ceiling(rand()*150+50)whereid=@i set@i=@i-1 id是表A里的自增长列,不清楚你的表里有没有,若是没有的话,可以自己造个临时表,插入数据。 本回答由提问者推荐 UUID是一个由5位十六进制数的字符串表示的128比特数字,其格式为aaaaaaaa-

    2023年04月11日
    浏览(45)
  • 一文详解安全随机数

    本文分享自华为云社区《【安全攻防】深入浅出实战系列专题-安全随机数》,作者: MDKing 。 使用随机数可分类安全场景跟非安全场景。非安全场景需要生成的越快越好。安全场景使用的随机数必须足够安全,保证不能被预测到。 常见的非安全场景: 数据的索引号、标识;

    2024年02月05日
    浏览(46)
  • rexp() R函数,生成服从指数分布的随机数

    参考: R语言 【rexp】__BANA的博客-CSDN博客

    2024年02月07日
    浏览(38)
  • 【Python入门知识】NumPy 中的随机数及ufuncs函数

    前言 嗨喽~大家好呀,这里是魔王呐 ❤ ~! 什么是随机数? 随机数并不意味着每次都有不同的数字。随机意味着无法在逻辑上预测的事物。 伪随机和真随机 计算机在程序上工作,程序是权威的指令集。 因此,这意味着必须有某种算法来生成随机数。 如果存在生成随机数的程

    2024年02月03日
    浏览(98)
  • Java随机数之System/Random/SecureRandom详解

    本系列为:从零开始学Java,为千锋教育资深Java教学老师独家创作 致力于为大家讲解清晰Java学习相关知识点,含有丰富的代码案例及讲解。如果感觉对大家有帮助的话,可以【点个关注】持续追更~ 文末有本文重点总结!关于技术类问题,也欢迎大家和我们沟通交流! 我们在

    2024年02月06日
    浏览(62)
  • C语言随机数生成和范围设置详解【超详细教程】

    本文详细介绍了C语言中如何使用rand函数生成随机数以及利用srand函数设置随机数的种子,同时解释了如何控制随机数的范围。适合初学者学习和实践。

    2024年02月05日
    浏览(51)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包