C++ rand() 和 srand()
1、rand()不需要传入参数,使用该函数能够返回一个从0到最大随机数的任意整数,最大随机数的大小通常是固定的一个大整数。
2、在0 ~ 99 这100个整数中随机取一个整数
可以表示为:int num = rand() % 100;
3、如果下界不为零,例如要产生 1 ~ 100的数字
可以表示为:int num = rand() % 100 + 1;
4、一般表示为:int num = rand() % n +a;
其中的 a 是起始值,n - 1 + a 是终止值,n 是整数的范围。
5、若要产生0 ~ 1之间的小数,则可以先取得0~10的整数,然后均除以10即可得到“随机到十分位”的10个随机小数。
若要得到“随机到百分位”的随机小数,则需要先得到0~100的10个整数,然后均除以100(即取出的小数的精度由mod的值所决定)
代码
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
int main()
{
//取任意数,数的范围在0到一个比较大的数字之间
for(int i = 1; i <= 1e2; i++)
printf("%d\n", rand());
//在0到99中随机取一个数字
for(int i = 1; i <= 1e2; i++)
printf("%d\n", rand() % 100);
//在10到109中随机取一个数字
for(int i = 1; i <= 1e2; i++)
printf("%d\n", rand() %100 + 10);
//产生0 ~ 1之间的小数,具体的精度由mod决定
for(int i = 1; i <= 1e2; i++)
printf("%lf\n", (rand() % 10) * 1.0 / 10 );
return 0;
}
我们会发现,上面这段代码进行多次编译,结果都是一样的。
虽然rand()产生的数是随机数,但是这些是输出的结果在定义之后是不会再变化了(也就是编译器重新编译后输出的结果是相同的)。
如果这时候我们希望每次编译后输出的结果不相同,那么我们就需要用到srand() 和 time() 函数了。
time(0)可以输出一个与时间有关的数,再结合srand()函数即可产生真正的随机数.
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
int main()
{
srand(int(time(0)));
//取任意数,数的范围在0到一个比较大的数字之间
for(int i = 1; i <= 1e2; i++)
printf("%d\n", rand());
//在0到99中随机取一个数字
for(int i = 1; i <= 1e2; i++)
printf("%d\n", rand() % 100);
//在10到109中随机取一个数字
for(int i = 1; i <= 1e2; i++)
printf("%d\n", rand() %100 + 10);
//产生0 ~ 1之间的小数,具体的精度由mod决定
for(int i = 1; i <= 1e2; i++)
printf("%lf\n", (rand() % 10) * 1.0 / 10 );
return 0;
}
蒙特卡罗方法
蒙特卡罗方法,也称统计模拟方法,是一种以概率统计理论为指导的数值计算方法。是指使用随机数(或更常见的伪随机数)来解决很多计算问题的方法。
计算圆周率
用蒙特卡罗方法,让计算机每次随机生成两个0到1之间的数,看以这两个实数为横纵坐标的点是否在单位圆内。
生成一系列随机点,统计单位圆内的点数与总点数,当随机点获取越多时,其结果越接近于圆周率。
不过准确度还是不高:
首先,计算机产生的随机数是受到存储格式的限制的,是离散的,并不能产生连续的任意实数;
其次,上述做法将平面分割成一个个网格,在空间也不是连续的,由此计算出来的面积当然与圆或多或少有差距。
个人理解
就是先进行随机的操作,然后对这些操作记录进行统计,根据这些数据推测/获取答案的近似值。
我们用C中的rand()函数实现模拟。
参考来源
wiki百科
https://zh.wikipedia.org/wiki/蒙地卡羅方法
博客
https://www.cnblogs.com/yuehouse/p/10116691.html
博客
https://blog.csdn.net/zhuangjinhua/article/details/79940123