什么是猜数字游戏?
猜数字游戏,简单来说,就是在给定的一组数的范围内猜出提前设定好的数。那么,怎样提高我们的查找效率呢?简而言之,就是靠 “蒙”,但是呢,这个“蒙”也是需要技巧的,而我们所熟知的二分查找便是猜数字游戏的最佳解决方法。
解决思路
首先让程序自动生成一个随机的整数(1-100),用户来输入一个整数,系统会根据用户输入的情况来提示用户是猜高了还是猜低了,又或者是猜对了!这是一个大概的思路,下面我们来进行具体的代码实现!
代码实现
第一步,我们首先写一个简单的菜单函数,通过这个函数来和用户进行交互:
int menu(){
printf("====================\n");
printf("1.开始游戏\n");
printf("0.退出游戏\n");
printf("====================\n");
printf("请输入您的选择:");
int choice = 0;
scanf("%d", &choice);
return choice;
}
这里我们要注意的是在这个代码块里,我们最终的返回值是choice,而不是0;
scanf输入的如果是整数,则需要加上&,如果输入的是字符串,则把()里的%d改为%s,同时去掉&符号。
第二步,在上一步中,我们首先写了一个菜单函数,之后,我们需要写一个main()函数来对这个menu()做一个补充:
int main(){
srand(time(0));
while (1){
int choice = menu();
if (choice == 1){
game();
}
else if (choice == 0){
printf("退出程序!\n");
}
else{
printf("您的输入有误,请重新输入!\n");
}
}
}
如果用户输入1,则进行游戏,这里我们先引入一个game()函数,如果用户输入2,则直接退出游戏,如果用户输入的数字不是这两个数字,则提醒用户输入错误,请重新输入。
第三步,在有了main()函数之后,我们再对其中的game()函数做一个编写,要求是程序自动生成一个1-100的随机整数,从控制台读取用户的输入,然后再进行比较用户输入的数字和系统生成的数字之间的关系,并给出用户提示:
void game(){
int toGuess = rand() % 100 + 1;
while (1){
printf("请输入要猜的数字:");
int input = 0;
scanf("%d", &input);
if (input < toGuess){
printf("低了!\n");
}
else if (input>toGuess){
printf("高了!\n");
}
else{
printf("猜对了!\n");
break;
}
}
}
关于void game()与game()写法的说明
void game(){}
这里的void的意思是没有返回值,当别的函数调用此函数时,不需要返回值,则写成这样的形式,免用return语句。
game(){}
这种函数省略返回值类型的写法,在一些上古时代的书中出现过,这种情况表示默认函数的返回值类型就是int,但是这种写法其实是很老很老的c编译器支持的,现在不推荐这样写。
rand()函数
C语言中用来产生一个随机数的函数。 rand()函数不需要参数,它将会返回0到RAND_MAX之间的任意的整数。这里我们void game()函数代码块中的rand()%100+1的意思就是在1-100中随机取一个数。
伪随机数
计算机中生成随机数通常都是“伪随机”,使用一个数学公式,把初始值带入公式,就会得到一组数字序列,这一组序列中的数字彼此之间看起来没什么规律,就可以近似的认为这组数字是随机的数字。
rand()函数其实不是真正意义上的随机数生成器,rand()函数在使用的时候还需调用srand()函数,srand()函数会设置供rand()函数使用的随机数种子,每一个种子对应一组根据算法预先生成的随机数。随机种子相同,得到的随机序列就是相同的,随机种子不同,得到的随机数序列就是不同的。
srand()函数
对于在对srand的调用中使用的每个不同的种子值,可以预期伪随机数生成器在随后的对rand的调用中产生不同的结果序列。同一个种子的两个不同初始化将在后续调用RAND中产生相同的结果序列。如果种子设置为1,则生成器被重新初始化为其初始值,并产生与调用rand或srand之前相同的值。为了生成类似随机的数字,srand通常被初始化为一些独特的运行时值。
我们常常使用系统时间来初始化,使用time函数来获取系统时间,得到的值是一个时间戳,即从1970年1月1日0点到现在时间的秒数,然后将得到的time_t类型数据转化为(unsigned int)的数,然后再传给srand函数。
变量/函数常见的命名风格
1.小驼峰命名法:toGuess -----第一个单词首字母小学,后续的单词首字母大写;
2.大驼峰命名法:ToGuess-----每个单词的首字母都是大写;
3.蛇形命名法:to_guess-----单词之间使用_分割,统一使用小写字母;
4.脊柱命名法:to-guess-----单词之间使用-分割,统一使用小写字母;
5.匈牙利命名法:iToGuess-----首字母是一个表示类型的缩写,i表示是int;s表示字符串;c表示字符…
总代码
#define _CRT_SECURE_NO_WARNINGS
#include<stdio.h>
#include<stdlib.h>
#include<time.h>
int menu(){
printf("====================\n");
printf("1.开始游戏\n");
printf("0.退出游戏\n");
printf("====================\n");
printf("请输入您的选择:");
int choice = 0;
scanf("%d", &choice);
return choice;
}
void game(){
int toGuess = rand() % 100 + 1;
while (1){
printf("请输入要猜的数字:");
int input = 0;
scanf("%d", &input);
if (input < toGuess){
printf("低了!\n");
}
else if (input>toGuess){
printf("高了!\n");
}
else{
printf("猜对了!\n");
break;
}
}
}
int main(){
srand(time(0));
while (1){
int choice = menu();
if (choice == 1){
game();
}
else if (choice == 0){
printf("退出程序!\n");
break;
}
else{
printf("您的输入有误,请重新输入!\n");
}
}
system("pause");
return 0;
}