C++11提供了很多的随机数生成器,可以使用均匀分布,正态分布等方法进行随机。
要想生成随机数,请包含random
头文件
C++11的随机数生成比C语言要麻烦,也好用地多。主要有以下概念:
- 随机数生成器:用来生成随机数的类,相比于C语言,C++通过提供不同的随机数生成器来提供不同的随机数生成算法,让用户对随机数生成的底层算法有更好的选择。
- 随机数分布:用于按照一定的分布来产生随机数。本质上是通过限定或修改随机数生成器产生的随机数来得到结果的,所以需要一个随机数生成器。
一般来说,得到一个随机数的方式如下:
- 首先得得到一个随机数生成器
- [可选] 然后可以采用随机数引擎适配器来对生成器进行一些操作
- 最后将生成的随机数传入随机数分布来得到随机数。
比较典型的过程如下:
|
|
随机数生成器
所谓的随机数生成器,其实就是生成随机数的底层算法。
所有的随机数生成器都是要传入种子的,使用成员函数seed(t)
即可传入,或者在构造时传入也行。
一般预定义的随机数生成器用的比较多。
随机数生成引擎
是一些通过特定算法生成随机数的类,一共有三个
linear_congruential_engine
:实现线性同余算法mersenne_twister_engine
:实现梅森缠绕器算法subtract_with_carry_engine
:实现带进位减(一种延迟斐波那契)算法
这些类都是模板类,其模板参数是要生成的随机数类型和算法需要的一些参数(具体见cppreference)
随机数引擎适配器
用于和随机数引擎搭配使用的适配器类,主要是修改引擎随机出来的随机数,一共有三个:
discard_block_engine
:舍弃随机数引擎的某些输出independent_bits_engine
:将一个随机数引擎的输出打包为指定位数的块shuffle_order_engine
:以不同顺序将随机数引擎的结果输出
都是模板类,其模板参数的第一个是随机数引擎的类型,其他的则是需要的参数。
预定义的随机数生成器
这里定义了一些包装了比较流行的算法包的生成器,这里仅举例一些常用的:
mt19937
:32位梅森缠绕器算法mt1993_64
:64位梅森缠绕器算法default_random_engin
:默认随机数生成器
一般的用法如下:
|
|
非确定随机数生成器
可以说是真正意义上的随机数(不过具体的还是得看实现,Linux下是通过读取/dev/urandom
文件来实现随机的,这就是真正的随机数。而Window则是偷懒直接使用rand_s()
函数,这就还是伪随机数)
random_device
:非确定随机数生成器
一般由于random_device
产生随机数的能力很强,我们一般用其产生的随机数当做其他随机数生成器或引擎的种子。
随机数分布
通过限定或者修改随机数生成器的结果来达到一定程度的分布。所以一般参数都需要有一个随机数生成器。
下面列举一些常用的:
uniform_int_distribution
/uniform_real_distribution
:产生一个在区间*[a,b]*上的均匀随机数(分别产生整数和浮点数)binomial_distribution
:二项分布poisson_distribution
:泊松分布normal_distribution
:正态分布
一般的用法如下:
|
|