C++中生成随机数即可以使用C语言中的rand和srand的方式,也可以使用C++11中的random类。
cstdlib中伪随机数
C语言中通过函数rand
和srand
来产生伪随机数,这两个函数包含在头文件cstdlib
中,其中srand
用来产生设置随机数种子,rand
每次返回一个当前的种子对应的随机数,这两个函数的声明如下:
1 | void srand(unsigned seed); |
这两个函数的原型形如:
1 | unsigned long int next = 1; |
显然rand只能生成整数,需要小数时,只需要跟一个浮点数进行除法即可
一个生成[1, 15]的随机数例子:
1 |
|
生成指定范围的随机数表达式:
要取得[a,b)的随机整数,使用(rand() % (b-a))+ a;
要取得[a,b]的随机整数,使用(rand() % (b-a+1))+ a;
要取得(a,b]的随机整数,使用(rand() % (b-a))+ a + 1;
通用公式:a + rand() % n;其中的a是起始值,n是整数的范围。
要取得a到b之间的随机整数,另一种表示:a + (int)b * rand() / (RAND_MAX + 1)。
要取得0~1之间的浮点数,可以使用rand() / double(RAND_MAX)。
C++11中的random类
random类是C++11中增加的类,该类可以用于生成随机数,具有C语言中rand生成伪随机数的功能,但其功能更强大。原生支持生成浮点数,及分布类。
随机数发生器主要由分布对象和随机数引擎对象组成。其中随机数引擎用于根据随机数种子来产生随机数,分布对象对产生的随机数根据需求进行分布。
random中定义了多种随机数引擎及分布类型,常用的引擎是默认伪随机数引擎类default_random_engine
,常用的分布类有产生整型分布的uniform_int_distribution
,产生浮点型的分布uniform_real_distribution
。
举例
该程序输出15个double类型的随机数
1 |
|
需要注意
1.一个给定的随机数发生器一直会生成相同的随机数序列。一个函数如果定义了局部的随机数发生器,应该将其(包括引擎和分布对象)定义为static的,否则每次调用函数都会生成相同的序列。也就是说定义成static后每次调用还是之前那个发生器,第一次调用产生一批随机数,再次调用将产生接下来的随机数,否则每次调用产生的都是最前面的那些随机数。
2.依然需要使用time来做为种子产生每个不同时刻都不同的随机序列,但由于time默认返回的是以秒计的时间,所以有可能多次使用的都是相同的种子。
伪随机数引擎
1.随机数引擎支持的操作如下:
- Engine e; //默认构造函数,使用该引擎类型的默认种子
- Engine e(s); //使用整型s做为种子
- e.seed(s); //使用整型s重置引擎状态
- e.min(); //返回此引擎所能生成的最小和最大值
- e.max();
- Engine::result_type //此引擎生成的类型(unsigned)
- e.discard(u); //将引擎推进u步,u为unsigned long long类型
2.随机数引擎使用
1 | std::default_random_engine e; //生成随机的无符号数 |
分布
1.分布类型有很多种,常用的有返回整型的uniform_int_distribution
和返回浮点型的uniform_real_distribution
。
2.分布支持的操作
- Dist d; //默认构造函数
- Dist d(min, max); //为d指定范围
- d(e) //e是一个随机数引擎对象
- d.min() //返回d(e)所能生成的最小值和最大值
- d.max()
- d.reset(); //重置d的状态,使得随后对d的使用不依赖于d已经生成的值