实验一 随机数及其应用
题目
*本题皆要求真随机数。
设计一个程序,界面要求如下图:
① .选择“1”时,编写一个生成1到100随机数的自定义函数,并调用10000次,求随机数分布情况。
参考运行结果如下:
② .选择“2”时,制作一“35选7 ” 福利彩券摇奖器,即:每次运行随机产生7个1~35的不重复的整数。
参考运行结果如下:
③ .选择“3”时,制作一“x选y ”通用福利彩券摇奖器,即:每次运行,随机产生y个1~x的不重复的整数。 要求交互良好,使用方便。
参考运行结果如下:
说明
随机数的生成:
srand():设置随机数生成种子
rand():生成随机数
如果未设随机数种子,rand()在调用时会自动设随机数种子为1。
1.如果在程序运行时没有自主设置种子或者随机种子是一样的话,用函数rand产生的随机数序列会是固定的,无法达到真随机数的概念。
因此需要初始化随机函数种子,用srand((unsigned)time(NULL));,拿系统时间作为种子,由于时间是变化的,种子变化。这样可以在一点程度上达到真随机数的概念。
因为在用srand设置随机数种子后,可能产生不同的随机序列(概率很大)。之所以说以很大的概率产生不同的随机数序列,是因为从上面的解释可以看到,rand是以秒数为单位的。一旦程序多次运行的时间间隔少于1s。那么srand设置种子也没有什么用处。所以库函数产生随机数有一定的缺陷。
2.为了满足后俩题不重复的随机数的要求,需要在遇到重复的时候,重新进行生成随机数。
首先想到的是C++STL里的集合set,生成的随机数直接insert入set会自动排除重复数,最好返回set的长度,符合输出就行了,但set会自动帮元素排序,与题目稍有区别。
因此,这里选择使用0,1来进行标记随机数是否已经出现的方法。
注:生成x到y的随机数m:m=rand()%(b-a+1)+a;
具体看代码中的注释。
代码
(因为是作业,所以就不用奇奇怪怪的方法了)
#include <stdio.h>
#include <stdlib.h> //rand()、srand()函数调用
#include <time.h> //使用当前时钟做种子
#include <process.h>
#include <string.h>
int ichoice() /*选择操作参数*/
{
int mychoice;
system("CLS");//清屏
printf("\n");
printf(" 程序设计与实践 实验(一)随机数及其应用\n");
printf("\n");
printf(" ------随机数及其应用------ \n");
printf("\n");
printf(" 1 - 求随机数分布情况.\n");
printf(" 2 - '35选7'福利彩券摇奖器.\n");
printf(" 3 - 'x选y'通用福利彩券摇奖器.\n");
printf(" 0 - 结 束.\n");
printf("\n");
printf(" 请输入你的选择:");
scanf("%d",&mychoice);
return mychoice;
}
int random_100()//1到100随机数
{
int m;
m=rand()%100+1;
return m;
}
int random(int a,int b)//x到y随机数
{
int m;
m=rand()%(b-a+1)+a;
return m;
}
int sjs100()/*求随机数分布情况*/
{
int a[101]={0};//用以计数
int n;
printf("\n");
printf("求随机数分布情况\n");
for(int i=1;i<=10000;i++){
n=random_100();//调用随机数1-100生成函数
a[n]++;
}
for(n=1;n<=100;n+=4){
printf("%3d:--%3d %3d:--%3d %3d:--%3d %3d:--%3d\n",n,a[n],n+1,a[n+1],n+2,a[n+2],n+3,a[n+3]);
}
return 0;
}
int x_x()/*"35选7" 福利彩券摇奖器*/
{
int b[36]={0};//初始化 并登记序号状态 0未取出 1已取出
printf("\n");
printf("‘35选7’福利彩券摇奖器产生的结果:\n");//35 不放回取出
int k;
for(int i=0;i<7;i++){//计数器i,确保最终结果输出7个随机数
k=random(1,35);//1到35随机数
if(b[k]==0){
printf("%5d\n",k);//如果未取出,则输出此数
b[k]=1; //并标记为已取出
}
else i--;//如果该随机数已取出,则计数器i-1
}
return 0;
}
int x_y()/*"x选y"通用福利彩券摇奖器*/
{
int x,y;
printf("\n");
printf("‘x选y’通用彩券摇奖器,请输入x和y:");
scanf("%d%d",&x,&y);
int b[x+1]={0};
printf("‘%d选%d’福利彩券摇奖器产生的结果:\n",x,y);
int k;
for(int i=0;i<y;i++){
k=random(1,x);//1到x随机数
if(b[k]==0){
printf("%5d\n",k);
b[k]=1;
}
else i--;
}
return 0;
}
int main(void)
{
int choice;
srand((unsigned)time(NULL));// 使用每一次运行程序的时间作为随机数种子,之后用rand产生不可预见的随机序列
while((choice=ichoice())!=0)
{
switch(choice)
{
case 1:
sjs100();system("pause");break;/*求随机数分布情况*/
case 2:
x_x();system("pause");break; /*"35选7" 福利彩券摇奖器*/
case 3:
x_y();system("pause");break; /*"x选y"通用福利彩券摇奖器*/
default:
printf("Input Error.");system("pause");break;
}
}
return 0;
}