rand函数
作用
在运行程序后被调用时返回一个 0 ~ 32767 间的随机数
语法
需要的头文件为:stdlib.h
#include<stdlib.h>
int main()
{
int a = rand();
return 0;
}
缺陷
#include<stdlib.h>
#include<stdio.h>
int main()
{
int i = 0;
for (; i < 10; i++)//一个循环 10 次打印“随机值”的 for 语句
{
int a = rand();
printf("%d\n", a);
}
return 0;
}
当我们反复运行以上程序不难发现,打印出的随机数顺序都是一样的,都是:
41
18467
6334
26500
19169
15724
11478
29358
26962
24464
于是我们需要引入 srand 函数
srand 函数
作用
用于给函数 rand 设置种子
不同种子下生成随机数的规则不一致
语法
需要的头文件为:stdlib.h
#include<stdlib.h>
int main()
{
srand(unsigned int);//无符号的整型
int a = rand();
return 0;
}
示例
#include<stdio.h>
#include<stdlib.h>
int main()
{
srand(10);//将随机数种子设为 10
int i = 0;
for (; i < 10; i++)//一个循环 10 次打印“随机值”的 for 语句
{
int a = rand();
printf("%d\n", a);
}
return 0;
}
我们将最开始的实例加上 srand 后发现,得到的”随机数“确实不一样了:
71
16899
3272
13694
13697
18296
6722
3012
11726
1899
但是如果生成随机数的种子不变,每次运行程序后生成的顺序仍然一样
也就是说我们需要用 srand 函数给 rand 函数生成一个随机数作为种子
我们需要生成一个随机数,但生成一个随机数需要一个随机数,所以我们要生成一个随机数作为随机数用来生成随机数(bushi
那这个问题该怎么解决呢?
time 函数
作用
获取当前时间戳
时间戳是什么?
以下来自百度百科:
时间戳是指格林威治时间1970年01月01日00时00分00秒(北京时间1970年01月01日08时00分00秒)起至现在的总秒数。
也就是说时间戳是在不断变化的
语法
需要的头文件为:time.h
time(指针);
示例
#include<stdio.h>
#include<time.h>
int main()
{
int a = time(NULL);//给 time 函数传递一个空指针
printf("%d",a);
return 0;
}
当每次运行以上程序后我们发现:打印出的值在不断增加
于是我们就可以用时间戳作为生成随机数的种子
实现完全随机
原理
正如上文所说:用时间戳作为生成随机数的种子
一个不当的实例
#include<Windows.h>//Sleep 函数的头文件
#include<time.h>
#include<stdio.h>
#include<stdlib.h>
int main()
{
int b = 0;
while (1)
{
unsigned int seed = time(NULL);//定义局部变量 seed,并将时间戳赋值给 seed
srand(seed);//设置随机数种子
b = rand();//获取随机数
printf("%d\n", b);//打印出获取的随机数
Sleep(1000);//暂停 1000ms ,也就是暂停 1s
}
return 0;
}
在这里我们无需过多关注 Sleep 函数和 Windows.h
以上程序运行后在屏幕上打印出的数字呈现某种连续性:
29772
29775
29779
29782
29785
29788
29792
29795
29798
29801
29805
29808
...
这是由于:
以上程序将设置随机数种子的部分放在了循环内,
导致每次设置随机数种子后只打印该种子下的第一个随机数,
随后又重新设置种子
于是,我们得出结论:在需要生成随机数时,设置随机数种子的部分在整个程序中最好只运行一次
对于以上实例,我们只要将设置随机数种子的部分放至循环体外部即可
正确的实例
将设置随机数种子的部分放在循环体外,使得运行一次程序只设置一次种子
#include<Windows.h>
#include<time.h>
#include<stdio.h>
#include<stdlib.h>
int main()
{
unsigned int seed = time(NULL);
srand(seed);//将设置随机数种子的部分放在循环体外,使得运行一次程序只设置一次种子
int b = 0;
while (1)
{
b = rand();
printf("%d\n", b);
Sleep(1000);
}
return 0;
}
某次运行结果:
30846
14300
24092
15809
26965
513
13552
30653
25913
24850
11981
5943
26837
5208
11753
...
限制范围
原理
通过取模操作可以使生成的这个范围在 0~32767 间的数字范围缩小
示例( r 为生成的随机数)
r % b
该式的结果即为 r 除以 b 的余数,可能取值为:0,1,2...b - 2,b - 1
可以得到范围限制在 [ 0 , n - 1 ] 的随机数
如果要限制的范围最小值不为 0 ,那么可以再加上一个数
r % b + c
可以得到范围限制在 [ c , b - 1 + c ] 的随机数
示例
#include<time.h>
#include<stdlib.h>
#include<stdio.h>
int main()
{
srand((unsigned int)time(NULL));
int a = 0;
int i = 0;
int b = 100;
int c = 10;
for (; i < 100; i ++)
{
a = (rand() % b + c);
printf("%d\n", a);
}
return 0;
}
以上的 b 为区间宽度 + 1,c 为区间最小值
会将 a 的范围限制在 [10,109]
例如:要使得随机值范围在 [15,300] 之间的话
c == 15
计算可知区间长度 b == 275 + 1 == 276
a = (rand() % 276 + 15);
应用
这种方法通常在写一些小游戏比如扫雷、三子棋(井字棋)、猜数游戏等。
都看到这了,不考虑点点关注什么的......
如果你对上面提到的几个小游戏感兴趣,那么我后面也会出相关的文章教程哦~
所以现在就______我,防止以后找不到
(疯狂暗示)