小游戏-扫雷

news/2024/5/18 14:45:18 标签: c语言, visual studio, 算法, 游戏程序

扫雷大多人都不陌生,是一个益智类的小游戏,那么我们能否用c语言来编写呢,

我们先来分析一下扫雷的运行逻辑,

首先,用户在进来时需要我们给与一个菜单,以供用户选择,

然后我们来完善一下,写出用户输入后对应要进行的内容,

game函数就是我们要写的扫雷的具体操作了,

首先我们来分析一下扫雷游戏的运行原理,

扫雷需要一个表格,可能是9*9,也可能是15*15,我们就拿9*9举例,

我们首先需要对这个9*9的表格进行埋雷,那用什么来代表我这个格子是不是雷呢,

我们可以用两个不同的字符来代替,我们假设’1‘为雷,’0‘没有雷,

转化为程序语言,表格我们用二维数组,埋雷用rand函数(rand函数在之前的文章中有讲述,没有学过的同学可以看一下,在“小游戏-猜数字”中)。

下面是我们的9*9棋盘,0代表还没有埋雷,

000000000
000000000
000000000
000000000
000000000
000000000
000000000
000000000
000000000

下面我们随即在其中埋几个雷,

000000000
000101000
010000000
000100000
000000000
001010001
000000000
000010000
001000000

雷埋好了,我们就要开始排雷了,

假如用户点击这个格子,如果没有雷,我们显示周围八个格子中的雷的数量,有雷的话,我们结束游戏,并展示我们埋的雷的情况,

这个格子周围有两个雷,那么我们在这个格子显示为2,

下面,用户继续点击其他格子进行排雷,

这个格子改为1,这个时候就会发现问题

如果用户接下来选择红色格子怎么办,灰色格子是我们更改后的雷的数量,并不代表这里有雷,这里就出现歧义了,那么我们现在应该怎么办呢?我们可以另外开辟一个表格来存放用户扫雷得到的信息,

设置数组大小的时候我们要注意一个点,当用户点到边缘的格子时,周围就不是八个格子了,这时我们去访问就会有越界的情况出现,

那这个时候我们应该怎么办呢,

我们可以在外面再加一圈,变成11*11的表格,但是在埋雷和让用户选择的时候不使用最外层,

00000000000
00000000000
00001010000
00100000000
00001000000
00000000000
00010100010
00000000000
00000100000
00010000000
00000000000

这个时候我们再去访问就不会有越界的情况了,而且在查雷的数量时,也不会有影响,

分析的差不多了,那么我们现在来把想法转换成代码,

我们新建两个文件,一个头文件,一个.c文件,我们声明两个变量放在.h头文件中,

那么我们想要在源.c中用的话就要在源.c中包含头文件#include“扫雷.h",同时我们设置出两个数组,

这里有疑问的朋友可以浏览一下我上面发布的那篇文章(文章标题:”在面对一个大型的代码,需要分文件编写的时候,应该怎么办呢;以及在编写出一个功能时,有人想要买这个功能,怎么在不给出源代码的情况下让买家可以使用这个代码功能呢?”),

下面我们开始埋雷,埋雷前,我们把两个数组初始化,下面的代码要注意都是写在了哪个文件中,

下面我将不再特意标明代码所处文件了,

初始化好后,我们开始随机埋雷,

雷布置完了,现在需要用户进行扫雷,但是扫之前,我们得让用户有选项来选择吧,我们把show棋盘打印给用户,

下面排查雷,

下面我们把游戏放到循环里,

下面我们把小错误改一下,并且完善一下我们的代码,

//源.c:
#define _CRT_SECURE_NO_WARNINGS 1

#include "扫雷.h"

void menu()
{
	printf("****************************\n");
	printf("*******   1 . play   *******\n");
	printf("*******   0 . exit   *******\n");
	printf("****************************\n");
}
 
void game()
{
	char mine[ROWS][COLS] = { 0 };//存放布置好雷的信息
	char show[ROWS][COLS] = { 0 };//存放排查出来的雷的信息用于显示
	//初始化棋盘 让mine棋盘埋好雷,show棋盘显示*
	//初始化mine棋盘
	//InitMine(mine, ROWS, COLS);
	//InitMine(show, ROWS, COLS);
	//在上面的代码中多增加一个实参,用于说明要初始化的内容
	InitMine(mine, ROWS, COLS,'0');
	InitMine(show, ROWS, COLS,'*');


	//打印show棋盘
	//Print(show, ROW, COL);//观察代码是否有问题

	//布置雷
	DisPlayBoard(mine, ROW, COL);
	//Print(mine, ROW, COL);
	Print(show, ROW, COL);

	//排查雷
	FindMine(mine, show, ROW, COL);
}

int main()
{
	int input = 0;
	srand((unsigned int)time(NULL));
	do
	{
		//菜单
		menu();
		printf("请选择:>");
		scanf("%d", &input);
		switch (input)
		{
			case 1:
				printf("--------    扫雷    --------\n");
				game();
				break;
			case 0:
				printf("退出游戏\n");
				break;
			default:
				printf("选择错误,请重新输入\n");
				break;
		}
	} while (input);
}
//扫雷.h:
#pragma once

#include<stdio.h>

#define EASY_COUNT 10//雷的数量

#define ROW 9 //雷的行
#define COL 9 //雷的列


//防止访问时越界
#define ROWS ROW+2 
#define COLS COL+2 

//棋盘初始化
void InitMine(char board[ROWS][COLS], int rows, int cols,char set);

//打印棋盘
void Print(char board[ROWS][COLS], int row, int col);

//布置雷
void DisPlayBoard(char board[ROWS][COLS], int row, int col);

//排查雷
void FindMine(char mine[ROWS][COLS], char show[ROWS][COLS], int row, int col);
//扫雷.c:
#define _CRT_SECURE_NO_WARNINGS 1


#include"扫雷.h"

//初始化mine棋盘均为字符‘0’
void InitMine(char board[ROWS][COLS], int rows, int cols,char set)
{
	for (int i = 0; i < rows; i++)
	{
		for (int j = 0; j < cols; j++)
		{
			board[i][j] = set;
		}
	}
}

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

//布置雷
void DisPlayBoard(char board[ROWS][COLS], int row, int col)
{
	int x = 0, y = 0;//代表布置雷的横纵坐标
	for (int i = 1; i <= EASY_COUNT; i++)
	{
		x = rand() % ROW + 1;
		y = rand() % COL + 1;
		if (board[x][y] == '1')
		{
			i--;
		}
		board[x][y] = '1';
	}
}

//排查雷

int Count(char board[ROWS][COLS], int x, int y)
{
	return board[x - 1][y - 1] + board[x - 1][y]
		+ board[x - 1][y + 1] + board[x][y - 1]
		+ board[x][y + 1] + board[x + 1][y - 1]
		+ board[x + 1][y] + board[x + 1][y + 1]
		- 8 * '0'; //这里将字符转化为数值
}

void FindMine(char mine[ROWS][COLS], char show[ROWS][COLS], int row, int col)
{
	//for (int i = 1; i <= row * col - EASY_COUNT; i++)
	int i = row * col - EASY_COUNT;
	while(i)
	{
		printf("请输入要排查雷的坐标:>");
		int x = 0, y = 0;
		scanf("%d%d", &x, &y);
		if (x <= row && y <= col && x>=1 && y>=1)
		{
			if (mine[x][y] == '1')
			{
				printf("很遗憾,你被炸死了\n");
				
				break;
			}
			else
			{
				//统计mine中这个坐标周围有几个雷
				int count = Count(mine, x, y);
				show[x][y] = count + '0';//转化为字符
				Print(show, ROW, COL);
				i--;
			}
		}
		else
		{
			printf("请输入正确的坐标\n");
		}
	}
	if (i == 0)
	{
		printf("恭喜你!\n");
	}
	Print(mine, ROW, COL);
}


http://www.niftyadmin.cn/n/5449086.html

相关文章

JavaScript中的正则表达式使用总结

JavaScript中的正则表达式是一种强大的工具&#xff0c;用于处理文本数据&#xff0c;包括搜索、匹配和替换文本中的特定字符或模式。以下是对JavaScript中正则表达式使用的一些总结&#xff1a; 1. 创建正则表达式 在JavaScript中&#xff0c;你可以使用字面量或RegExp对象来…

基础篇Redis

基础篇Redis 1.Redis简单介绍 Redis是一种键值型的NoSql数据库&#xff0c;这里有两个关键字&#xff1a; 键值型NoSql 其中键值型&#xff0c;是指Redis中存储的数据都是以key.value对的形式存储&#xff0c;而value的形式多种多样&#xff0c;可以是字符串.数值.甚至json…

权限提升-Windows权限提升篇数据库篇MYSQLMSSQLORACLE自动化项目

知识点 1、Web到Win-数据库提权-MSSQL 2、Web到Win-数据库提权-MYSQL 3、Web到Win-数据库提权-Oracle 章节点&#xff1a; 1、Web权限提升及转移 2、系统权限提升及转移 3、宿主权限提升及转移 4、域控权限提升及转移 基础点 0、为什么我们要学习权限提升转移技术&#xff1…

分类预测 | Matlab实现CNN-LSTM-Mutilhead-Attention卷积神经网络-长短期记忆网络融合多头注意力机制多特征分类预测

分类预测 | Matlab实现CNN-LSTM-Mutilhead-Attention卷积神经网络-长短期记忆网络融合多头注意力机制多特征分类预测 目录 分类预测 | Matlab实现CNN-LSTM-Mutilhead-Attention卷积神经网络-长短期记忆网络融合多头注意力机制多特征分类预测分类效果基本介绍模型描述程序设计参…

实现Spring Web MVC中的文件上传功能,并处理大文件和多文件上传

实现Spring Web MVC中的文件上传功能&#xff0c;并处理大文件和多文件上传 在Spring Web MVC中实现文件上传功能并处理大文件和多文件上传是一项常见的任务。下面是一个示例&#xff0c;演示如何在Spring Boot应用程序中实现这一功能&#xff1a; 添加Spring Web依赖&#x…

代码随想录算法训练营day19 | 二叉树阶段性总结

各个部分题目的代码题解都在我往日的二叉树的博客中。 (day14到day22) 目录 二叉树理论基础二叉树的遍历方式深度优先遍历广度优先遍历 求二叉树的属性二叉树的修改与制造求二叉搜索树的属性二叉树公共最先问题二叉搜索树的修改与构造总结 二叉树理论基础 二叉树的理论基础参…

TCP重传机制详解——03DSACK

TCP重传机制详解——03DSACK 什么是DSACK DSACK是指"Duplicate Selective Acknowledgment"&#xff0c;即重复选择性确认。在TCP通信中&#xff0c;DSACK机制允许接收方向发送方发送有关重复数据包的信息&#xff0c;以帮助发送方更准确地处理重传和丢包情况。 当…

语言模型的原理、实战与评估

语言模型的原理、实战与评估是一个宽泛的话题,下面是对这三个方面简要概述: 语言模型的原理 语言模型(Language Model, LM)是一种统计模型,用于估计一段文本序列的概率分布。它的核心任务是给定一系列词语,计算出这些词语组合成一个完整句子或段落的概率。典型的语言模型…