C语言实现低配版“扫雷”小游戏

2023-11-05 17:20

本文主要是介绍C语言实现低配版“扫雷”小游戏,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

C语言实现“低配版”——扫雷小游戏

​ 用C语言完成的小游戏——“扫雷”,这是一个有年代感的游戏,经久不衰也恰恰证明了这款游戏的趣味性,接下来,就用我们的所学来实现这个游戏。

​ 游戏例图:

游戏开始
游戏结束

​ 首先,我们应该先思考如何去一步步完成它,开始我们建立3个主要文件。mine

mine_sweeps.c mine_sweeps.h test.c

mine_sweeps.c 用于存放函数体的文件。

mine_sweeps.h 用于存放全局变量和头文件还有mine_sweeps.h中的函数声明

test.c是用来测试游戏的可行性

在test.c搭建基本选项
void menu()
{printf(" *******************\n");printf(" |     1.play      |\n");printf(" |     0.exit      |\n");printf(" ******************\n");
}
int main()
{srand((unsigned int)time(NULL));//随机数生成函数int input = 0;do {menu();printf("plase input number:>");scanf("%d", &input);//分支选择switch (input){case 1://开始游戏mine_sweep();break;case 0://退出游戏printf("game over!\n");break;default://重新输入printf("input wrong,plase input again!\n");break;}} while (input);return 0;
}

输入不同的数字会有不同的提示,这一点的设计会让玩家清楚现在正处于什么形势。

mine_sweep.h设计函数的实现和理清游戏步骤

#pragma once
//实现游戏需要包含的头文件
#include<stdio.h>
#include<stdlib.h>
#include<time.h>//含雷棋盘
#define ROW 9
#define COL 9
//实际棋盘
#define ROWS ROW+2
#define COLS COL+2
//雷数量
#define MINE 10//控制游戏体验//初始化数组
void init_board(char board[ROWS][COLS], int row, int col,char set);
//打印棋盘
void print_board(char board[ROWS][COLS], int row, int col);
//布置雷
void set_board(char board[ROWS][COLS], int row, int col);
//排查雷
void find_board(char board[ROWS][COLS],char show[ROWS][COLS],int row,int col);

此文件主要是函数声明和宏,改变其中数字可以把难度提升!!!

“mine_sweeps.c”

里面包含了游戏实现需要的主要函数

初始化棋盘函数,其中传递的字符决定了打印的效果。

//初始化棋盘
void init_board(char board[ROWS][COLS], int row, int col, char set)//set是将函数初始化
{int i = 0;for (i = 0; i < row; i++){int j = 0;for (j = 0; j < col; j++){board[i][j] = set;}}
}

打印棋盘函数,要注意打印的效果,特别是行号和列好的控制,虽然两个数组是11x11,但是我们实际打印的只有9x9。

//打印棋盘
void print_board(char board[ROWS][COLS], int row, int col)
{int i = 0;//打印列号for (i = 0; i <=col; i++){printf("%d ", i);}printf("\n");for (i = 1; i <= row; i++){//打印行号printf("%d ", i);int j = 0;for (j = 1; j <= col; j++){printf("%c ", board[i][j]);}printf("\n");}
}

布置雷函数,要使用我们设定好的数量然后放置相同数量的雷,可以设定count等于雷的数量,千万不可以用于++或者–,因为宏不可赋值。

//布置雷
void set_board(char board[ROWS][COLS], int row, int col)
{int count = MINE;while (count){int x = rand() % row + 1;//随机数库函数int y = rand() % col + 1;//随机数库函数if ('0' == board[x][y]){board[x][y] = '1';//含雷先设定为字符1count--;}}
}

生成随机数的函数:rand,是跟随srand一起使用的库函数。使用时必须引用 stdilb.h 头文件。srand生成的随机数会被rand接收,不过这个函数生成随机数是需要一个随机数来转换成随机数,这时候就要使用到我们的时间戳——time库函数,使用时必须引用 time.h头文件。这时候在main函数中将一个空指针传递给我们的time(NULL)就可以产生随机数了!!在使用rand时需要产生你需要的数字需要使用算数操作符,比如你需要0~9的数字,只需要rand%10。

排查雷函数主要是用于最后玩家输入的游戏体验,需要合适的提示和界面打印。

//排查雷
void find_board(char board[ROWS][COLS], char show[ROWS][COLS], int row, int col)
{int x = 0;int y = 0;int win = 0;;while (win<row*col-MINE){printf("please input x y:>");scanf("%d %d", &x, &y);if (x > 0 && x < row  && y>0 && y < col){if ('1' == board[x][y]){printf("很遗憾,你被炸死了*_*\n");print_board(board, ROW, COL);}else{//统计雷的个数int count=count_board(board, x, y);//返回的值就是该位置九宫格里的含雷数show[x][y] = count+'0';print_board(show, ROW, COL);win++;}}else{printf("x,y wrong,please input again!\n");}}if (win==col*row-MINE)printf("YOU WINING!!!\n");
}

统计雷函数不用在mine_sweep.h中声明的函数,因为他是用于排查雷需要的函数,具体如下:

//统计雷
int count_board(char board[ROWS][COLS],int x, int y)
{int count = 0; count += '0';count=board[x-1][y-1]+board[x-1][y]+board[x-1][y+1]+board[x][y-1]+board[x][y]+board[x][y+1]+board[x+1][y-1]+board[x+1][y]+board[x+1][y+1]-9 * '0';return count;
}

以上是每个函数的实现。

具体组成

mine_sweep.h

#pragma once
#include<stdio.h>
#include<stdlib.h>
#include<time.h>//含雷棋盘
#define ROW 9
#define COL 9
//实际棋盘
#define ROWS ROW+2
#define COLS COL+2
//雷数量
#define MINE 80//初始化数组
void init_board(char board[ROWS][COLS], int row, int col,char set);
//打印棋盘
void print_board(char board[ROWS][COLS], int row, int col);
//布置雷
void set_board(char board[ROWS][COLS], int row, int col);
//排查雷
void find_board(char board[ROWS][COLS],char show[ROWS][COLS],int row,int col);

mine_sweep.c

#define _CRT_SECURE_NO_WARNINGS 1#include"mine_sweep.h"//初始化棋盘
void init_board(char board[ROWS][COLS], int row, int col, char set)
{int i = 0;for (i = 0; i < row; i++){int j = 0;for (j = 0; j < col; j++){board[i][j] = set;}}
}//打印棋盘
void print_board(char board[ROWS][COLS], int row, int col)
{int i = 0;//打印列号for (i = 0; i <=col; i++){printf("%d ", i);}printf("\n");for (i = 1; i <= row; i++){//打印行号printf("%d ", i);int j = 0;for (j = 1; j <= col; j++){printf("%c ", board[i][j]);}printf("\n");}
}//布置雷
void set_board(char board[ROWS][COLS], int row, int col)
{int count = MINE;while (count){int x = rand() % row + 1;int y = rand() % col + 1;if ('0' == board[x][y]){board[x][y] = '1';count--;}}
}//统计雷
int count_board(char board[ROWS][COLS],int x, int y)
{int count = 0; count += '0';count=board[x-1][y-1]+board[x-1][y]+board[x-1][y+1]+board[x][y-1]+board[x][y]+board[x][y+1]+board[x+1][y-1]+board[x+1][y]+board[x+1][y+1]-9 * '0';/*count=mine[x - 1][y - 1] +mine[x][y - 1] +mine[x + 1][y - 1] +mine[x - 1][y] +mine[x + 1][y] +mine[x - 1][y + 1] +mine[x][y + 1] +mine[x + 1][y + 1] - 8 * '0';*/return count;
}
//排查雷
void find_board(char board[ROWS][COLS], char show[ROWS][COLS], int row, int col)
{int x = 0;int y = 0;int win = 0;;while (win<row*col-MINE){printf("please input x y:>");scanf("%d %d", &x, &y);if (x > 0 && x < row  && y>0 && y < col){if ('1' == board[x][y]){printf("很遗憾,你被炸死了*_*\n");print_board(board, ROW, COL);}else{//统计雷的个数int count=count_board(board, x, y);show[x][y] = count+'0';print_board(show, ROW, COL);win++;}}else{printf("x,y wrong,please input again!\n");}}if (win==col*row-MINE)printf("YOU WINING!!!\n");
}

test.c

```#define _CRT_SECURE_NO_WARNINGS 1
#include"mine_sweep.h"void menu()
{printf(" * ————————*\n");printf(" |     1.play      |\n");printf(" |     0.exit      |\n");printf(" * ————————*\n");
}void mine_sweep()
{char board[ROWS][COLS] = { 0 };//带雷char show[ROWS][COLS] = { 0 };//不带雷//初始化棋盘init_board(board, ROWS, COLS,'0');init_board(show, ROWS, COLS,'*');//打印棋盘//print_board(board, ROW, COL);print_board(show, ROW, COL);//布置雷set_board(board, ROW, COL);print_board(board, ROW, COL);//排查雷find_board(board, show, ROW, COL);}int main()
{srand((unsigned int)time(NULL));int input = 0;do {menu();printf("plase input number:>");scanf("%d", &input);switch (input){case 1:mine_sweep();break;case 0:printf("game over!\n");break;default:printf("input wrong,plase input again!\n");break;}} while (input);return 0;
}

以上就是该小游戏的全部函数,因为技术有限,并不能完全实现与电脑游戏一模一样的体验。不过我还是会继续深造,努力将他实现成原有的功能,谢谢观看😀。

这篇关于C语言实现低配版“扫雷”小游戏的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/351360

相关文章

C++中unordered_set哈希集合的实现

《C++中unordered_set哈希集合的实现》std::unordered_set是C++标准库中的无序关联容器,基于哈希表实现,具有元素唯一性和无序性特点,本文就来详细的介绍一下unorder... 目录一、概述二、头文件与命名空间三、常用方法与示例1. 构造与析构2. 迭代器与遍历3. 容量相关4

C++中悬垂引用(Dangling Reference) 的实现

《C++中悬垂引用(DanglingReference)的实现》C++中的悬垂引用指引用绑定的对象被销毁后引用仍存在的情况,会导致访问无效内存,下面就来详细的介绍一下产生的原因以及如何避免,感兴趣... 目录悬垂引用的产生原因1. 引用绑定到局部变量,变量超出作用域后销毁2. 引用绑定到动态分配的对象,对象

SpringBoot基于注解实现数据库字段回填的完整方案

《SpringBoot基于注解实现数据库字段回填的完整方案》这篇文章主要为大家详细介绍了SpringBoot如何基于注解实现数据库字段回填的相关方法,文中的示例代码讲解详细,感兴趣的小伙伴可以了解... 目录数据库表pom.XMLRelationFieldRelationFieldMapping基础的一些代

Java HashMap的底层实现原理深度解析

《JavaHashMap的底层实现原理深度解析》HashMap基于数组+链表+红黑树结构,通过哈希算法和扩容机制优化性能,负载因子与树化阈值平衡效率,是Java开发必备的高效数据结构,本文给大家介绍... 目录一、概述:HashMap的宏观结构二、核心数据结构解析1. 数组(桶数组)2. 链表节点(Node

Java AOP面向切面编程的概念和实现方式

《JavaAOP面向切面编程的概念和实现方式》AOP是面向切面编程,通过动态代理将横切关注点(如日志、事务)与核心业务逻辑分离,提升代码复用性和可维护性,本文给大家介绍JavaAOP面向切面编程的概... 目录一、AOP 是什么?二、AOP 的核心概念与实现方式核心概念实现方式三、Spring AOP 的关

从基础到高级详解Go语言中错误处理的实践指南

《从基础到高级详解Go语言中错误处理的实践指南》Go语言采用了一种独特而明确的错误处理哲学,与其他主流编程语言形成鲜明对比,本文将为大家详细介绍Go语言中错误处理详细方法,希望对大家有所帮助... 目录1 Go 错误处理哲学与核心机制1.1 错误接口设计1.2 错误与异常的区别2 错误创建与检查2.1 基础

Python实现字典转字符串的五种方法

《Python实现字典转字符串的五种方法》本文介绍了在Python中如何将字典数据结构转换为字符串格式的多种方法,首先可以通过内置的str()函数进行简单转换;其次利用ison.dumps()函数能够... 目录1、使用json模块的dumps方法:2、使用str方法:3、使用循环和字符串拼接:4、使用字符

Linux下利用select实现串口数据读取过程

《Linux下利用select实现串口数据读取过程》文章介绍Linux中使用select、poll或epoll实现串口数据读取,通过I/O多路复用机制在数据到达时触发读取,避免持续轮询,示例代码展示设... 目录示例代码(使用select实现)代码解释总结在 linux 系统里,我们可以借助 select、

Linux挂载linux/Windows共享目录实现方式

《Linux挂载linux/Windows共享目录实现方式》:本文主要介绍Linux挂载linux/Windows共享目录实现方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地... 目录文件共享协议linux环境作为服务端(NFS)在服务器端安装 NFS创建要共享的目录修改 NFS 配

通过React实现页面的无限滚动效果

《通过React实现页面的无限滚动效果》今天我们来聊聊无限滚动这个现代Web开发中不可或缺的技术,无论你是刷微博、逛知乎还是看脚本,无限滚动都已经渗透到我们日常的浏览体验中,那么,如何优雅地实现它呢?... 目录1. 早期的解决方案2. 交叉观察者:IntersectionObserver2.1 Inter