前言
今天我们来使用c语言做一个小游戏吧,这个游戏算是我们之前函数的一个应用,在这次的小游戏中我们会学习到rand函数的使用和时间戳的概念与使用,让我们来进行一个愉快的猜数字游戏吧!
题目
题目描述:
杰克又又又来了,有一天杰克想要玩游戏,但是呢,找不到好玩的游戏了,哎哟,该玩的都玩腻了,那就写一个游戏让杰克自娱自乐一下吧,我们写一个猜数游戏,不要很大,我们就写个可以猜到0~100之间数字的猜数游戏吧!
输入描述:
输入要猜的数字,与结果进行对比,如果没有猜对就重新输入。
输出描述:
首先输出一个菜单让用户选择是否进入游戏,1.play,表示进入游戏,0.exit,表示退出游戏,当猜数时猜大了就提醒玩家猜大了,猜小了就提醒玩家猜小了,如果猜中,告诉玩家:“恭喜你猜中了”。
题目分析
首先我们看看题目要求,我们需要输出一个0~100之间的随机数来使我们程序可以按照题目要求正常运行,这里我们使用rand函数来生成随机数,之后通过取模的方法来使rand可以生成0~100之间的随机数。
之后我们看到输出描述中的要求,我们需要一个菜单来存放1.play和0.exit使用户可以进行选择,那么这里我们使用函数的方式定义一个菜单来实现,当我们需要使用这个菜单的时候我们就对函数进行一个调用。
我们进入游戏,首先对游戏的结构进行一个分析,我们生成一个随机数之后,我们需要去猜那个数字,我们分为三个部分,我们猜大了,猜小了和猜中了,那么我们在猜随机数字的时候肯定不会一次性就猜到随机的数字是什么,那么这个时候我们就需要再猜一次,再猜一次,直到猜到系统生成的随机数字是多少。这里我们就需要一个循环结构,我们选择while循环。我们可以将这个游戏的进程定义为一个外部函数game,里面是我们游戏运行的基本逻辑。
之后我们定义主函数,在主函数中,我们首先调用之前定义的菜单,我们发现我们需要先进行一个函数的调用,这个时候我们想到了do...while的循环结构,之后我们使用switch语句来进行判断我们是否需要进入游戏。
好啦,整体的逻辑就是这个样子,让我们来看看代码吧
代码实现
#define _CRT_SECURE_NO_WARNINGS
#include<stdio.h>
#include<stdlib.h>
#include<time.h>
void menu()
{
printf("******************************\n");
printf("********* 1.play ***********\n");
printf("********* 0.exit ***********\n");
printf("******************************\n");
}
void game()
{
int guess;
//生成随机数
int ret = rand()%100+1;
//猜大
while (1)
{
printf("请输入您猜的数");
scanf("%d", &guess);
if (guess > ret)
{
printf("猜大了\n");
}
//猜小
else if (guess < ret)
{
printf("猜小了\n");
}
else
{
printf("恭喜你猜中了\n");
break;
}
}
}
int main()
{
int input = 0;
srand((unsigned int)time(NULL));
do
{
menu();
printf("请选择:>");
scanf("%d", &input);
switch (input)
{
case 1:
game();
break;
case 0:
printf("退出游戏\n");
break;
default:
printf("输入错误,重新选择\n");
break;
}
}
while (input);
return 0;
}
代码解析
首先我们完成了题目分析中提到的菜单,简单的定义menu,返回值为空,进行菜单的描述,我们使用*+字符的方式直接输出完成。
之后我们进行主函数的编写,我们使用do...while循环,调用menu使玩家选择是否进入游戏,这里我们使用shitch语句,当我们选择1的时候进入游戏,当我们选择0的时候退出游戏不用执行,使用case语句完成,之后我们需要考虑如果有玩家不小心输入错误该怎么办呢,我们想到switch还有一个default子句可以用来处理case语句处理不了的问题。所以当我们输入错误的数字之后我们需要提示玩家输入错误,请重新输入。
default子句解释:default子句是在switch循环中如果case语句的条件都没有达到的时候,如果设置了default子句的话程序会自动执行default子句下的内容。
在这里我们输入1之后进入程序,我们需要跳转到我们的游戏界面,那么我们如何跳入用户界面呢,这里我们使用函数完成,我们定义外部函数game作为我们进入游戏的媒介。
在我们自定义的函数game中,我们首先定义一个guess,guess为整型,设置输入用来存放我们到时候输入的数字。在定义输入scanf函数的时候,我们需要在之前加入一行代码用来提示用户,这个时候我们的游戏已经开始了,可以输入自己猜的数字了,使用printf函数之间输出:("请输入您猜的数");来完成。
我们使用if语句来对我们每次输入的数与随机数进行一个比较,猜大了对玩家进行输出猜大了,猜小了就对玩家输出猜小了,如果猜对了按照题目要求对玩家输出恭喜你猜中了。我们当然不会在猜一次之后就让程序结束,我们使用while循环,当我们在游戏开始的菜单界面选择输入1的时候,我们开始猜数游戏。
我们现在残留最大的问题就是,随机数应该怎么去生成,当我们使用rand函数生成随机数的时候我们发现,在转入它的定义的时候,我们发现rand生成随机数的最大值是0x7fff,它是一个16进制数,转换为10进制数为32767,所以这是我们现在生成随机数的区间。
在我们第二次运行程序的时候我们发现,程序虽然生成了随机数,但是和上一次生成的随机数字是一样的,我们需要去解决这个问题。
这里我们通过查询rand函数的使用方式的时候发现,在调用rand之前,我们还需要使用srand函数来设置我们随机数的生成器,srand函数应该怎么使用呢,我们查找资料发现,他的作用是设置一个随机的起点,并且,他需要一个无符号整型的数值unsigned int seed,这里的seed有种子的意思,它具体是一个用于初始化随机数生成器的初始值。
这里我们熟悉了rand函数和srand函数的使用方法之后我们再引入一个时间戳的概念,时间戳是一个用于记录特定事件发生时间的标记,通常表示为日期和时间的组合。我们设置种子seed为一个时间戳time(NULL),我们使用time函数完成,它的作用是获取系统时间,在使用的过程中我们发现time函数的使用需要一个参数叫time_t*timer,这里*timer是一个指针,这里我们不使用它,我们直接给time函数传一个空指针。
这里需要注意我们前面了解到srand函数需要一个无符号整型的数值,所以这里我们还需要对time函数的生成值进行一个强制类型的转换。
最后一步了,我们将生成的随机数进行模100之后得到的值给ret,万一级的单位在模100之后会生成0~99的余数,这里我们利用这个余数来进行对ret的赋值之后得到我们0~100的随机数,当然,我们这里想得到100的话需要在后面给它加一哦!
杰克玩到了他自己通过编程实现的游戏,很开心呢,我亲爱的读者们你们也是呢,希望你们可以从我的博客中学到一点的知识,如果有不足请指正哦!!