当前位置:   article > 正文

C语言应用实例——扫雷

C语言应用实例——扫雷

扫雷是一款经典的单人益智游戏,目标是在不触发地雷的情况下,揭开所有非地雷方格。本文将逐步介绍如何使用C语言编写一个简单的扫雷游戏。我们将从零开始,逐步完成代码,详细解释每一步的功能,最后呈现完整的扫雷游戏。

步骤1:设计游戏规则和数据结构

在设计扫雷游戏之前,首先需要定义游戏规则和数据结构。我们将使用以下规则:

  • 游戏区域是一个9x9的方格,共81个方格。(标准版)
  • 游戏开始时,随机分布10个地雷在这些方格中,地雷用'1'表示。
  • 玩家的目标是排查出所有的地雷,而不触发它们。
  • 玩家可以选择一个方格进行排查,如果排查的是地雷,游戏结束;如果排查的是空方格,将显示周围的地雷数量。
  • 游戏结束条件:玩家揭开了所有非地雷方格或触发了地雷。

为了实现这些规则,我们需要定义以下数据结构和函数:(函数声明存放在game.h头文件中)

数据结构

在扫雷游戏中,数据结构用于存储和管理游戏的状态、方格的内容以及其他关键信息。在我们的示例中,我们定义了以下数据结构:

  1. #define ROW 9
  2. #define COL 9
  3. #define ROWS (ROW + 2)
  4. #define COLS (COL + 2)
  5. #define EASY_COUNT 10
  6. char board[ROWS][COLS]; // 游戏区域
  7. char mine[ROWS][COLS]; // 存放地雷的信息
  8. char show[ROWS][COLS]; // 存放排查出的雷的信息
  • board[ROWS][COLS]:这是一个二维字符数组,表示整个游戏区域。它用于存储方格的状态,'0'表示未揭开的方格。

  • mine[ROWS][COLS]:同样是一个二维字符数组,用于存储地雷的分布情况。'1'表示在该方格中有地雷,'0'表示没有地雷。

  • show[ROWS][COLS]:也是一个二维字符数组,用于存储已排查出的方格的信息。在每个方格中,如果没有地雷,则显示周围地雷的数量,否则显示'1'表示地雷。

这些数据结构是游戏状态的核心,它们跟踪了游戏区域中每个方格的状态和内容,以便玩家可以与游戏进行交互并了解游戏进展。

函数声明

  1. void InitBoard(char board[ROWS][COLS], int rows, int cols, char set);
  2. void DisplayBoard(char board[ROWS][COLS], int row, int col);
  3. void SetMine(char board[ROWS][COLS], int row, int col);
  4. int GetMineCount(char mine[ROWS][COLS], int x, int y);
  5. void FindMine(char mine[ROWS][COLS], char show[ROWS][COLS], int row, int col);

在C语言中,函数声明用于告诉编译器有关函数的信息,包括函数名称、参数列表和返回类型。在示例中,我们声明了以下函数:

  1. void InitBoard(char board[ROWS][COLS], int rows, int cols, char set);
  2. void DisplayBoard(char board[ROWS][COLS], int row, int col);
  3. void SetMine(char board[ROWS][COLS], int row, int col);
  4. int GetMineCount(char mine[ROWS][COLS], int x, int y);
  5. void FindMine(char mine[ROWS][COLS], char show[ROWS][COLS], int row, int col);
  • InitBoard:这个函数用于初始化游戏棋盘,将所有方格的状态设置为指定字符(在这里是'0'),以表示方格都是未揭开的状态。

  • DisplayBoard:该函数用于打印游戏棋盘,将游戏区域的状态和内容显示在终端上,以供玩家查看。

  • SetMine:这个函数用于随机布置地雷,根据游戏规则在游戏区域内随机选择方格并设置为地雷状态。

  • GetMineCount:该函数计算指定方格周围的地雷数量,以便在揭开非地雷方格时显示周围的地雷数量。

  • FindMine:这个函数实现了游戏的核心逻辑,允许玩家逐步揭开方格,查找地雷,以及判定游戏是否胜利或失败。

我在这里额外补充一下:函数声明的作用是告诉编译器这些函数的存在和接口,以便在程序的其他部分使用这些函数,同时确保函数的调用是合法的。这有助于代码的模块化和可维护性,因为函数的实现可以在不同的源文件中完成,而不需要将所有代码都放在一个文件中。

你可能会对这之前的操作感到迷茫:这些函数声明看得我头晕,到底该怎样写?别急,且听我慢慢道来:

步骤2:初始化棋盘

为什么需要初始化棋盘?

在扫雷游戏中,初始化棋盘是游戏准备的第一步,目的是确保游戏开始时,所有方格都是未揭开的状态。这是因为玩家应该从一个空白的游戏区域开始,然后根据游戏规则逐步揭开方格。

通过初始化棋盘,我们为后续的游戏逻辑做好了准备,使得游戏的状态在开始时是清晰的。随着游戏的进行,玩家将逐步改变方格的状态,揭开非地雷方格并触发地雷,从而决定游戏的结果。

在扫雷游戏中,初始化棋盘是确保游戏开始正常的关键步骤,它提供了游戏的起点。一旦初始化完成,玩家就可以逐步揭开方格,探索地雷的分布,体验游戏的乐趣。

在步骤2中,我们实现了名为 InitBoard 的函数,它的作用是初始化游戏棋盘。以下是函数的声明和实现:

void InitBoard(char board[ROWS][COLS], int rows, int cols, char set);

char board[ROWS][COLS]:这是一个二维字符数组,用于表示游戏区域,ROWSCOLS 是游戏区域的行数和列数,set 是用来初始化每个方格的字符。

函数实现

函数的实现如下:

  1. void InitBoard(char board[ROWS][COLS], int rows, int cols, char set)
  2. {
  3. int i, j;
  4. for (i = 0; i < rows; i++)
  5. {
  6. for (j = 0; j < cols; j++)
  7. {
  8. board[i][j] = set;
  9. }
  10. }
  11. }

这个函数采用了以下步骤来初始化游戏棋盘:

  1. 使用两个嵌套的循环遍历所有方格,i 从 0 到 rows - 1,j 从 0 到 cols - 1
  2. 对每个方格,将其状态设置为 set,也就是传入的初始化字符,通常是 '0',表示未揭开的状态。

步骤3:打印棋盘

为什么需要打印棋盘?

打印游戏棋盘是扫雷游戏的一个关键功能,它有几个重要作用:

  1. 提供游戏视觉反馈: 游戏棋盘的打印使玩家能够实时看到游戏的状态,包括哪些方格已经揭开,哪些方格包含地雷,以及周围的地雷数量。这为玩家提供了重要的游戏信息,帮助他们决策下一步的操作。

  2. 交互性: 通过打印游戏棋盘,玩家可以选择要揭开的方格,根据所见到的信息决定哪些方格可能包含地雷,从而进行下一步的排查。玩家可以根据打印的棋盘状态与游戏进行交互。

  3. 游戏体验: 打印游戏棋盘提供了一种更好的游戏体验,让玩家更容易理解游戏的进展和结果。

打印棋盘的函数

在本步骤中,我们实现了名为 DisplayBoard 的函数,它的作用是打印游戏棋盘,将游戏区域的状态显示在终端上。以下是函数的声明和实现:

void DisplayBoard(char board[ROWS][COLS], int row, int col);
  • char board[ROWS][COLS]:这是一个二维字符数组,表示游戏区域的状态。ROWSCOLS 是游戏区域的行数和列数,rowcol 是实际要打印的行数和列数,通常比游戏区域的行数和列数少2,因为游戏区域的外围通常不显示。

函数实现

函数的实现如下:

  1. void DisplayBoard(char board[ROWS][COLS], int row, int col)
  2. {
  3. int i, j;
  4. printf(" ");
  5. for (i = 1; i <= col - 2; i++)
  6. {
  7. printf("%d ", i);
  8. }
  9. printf("\n");
  10. for (i = 1; i <= row - 2; i++)
  11. {
  12. printf("%d ", i);
  13. for (j = 1; j <= col - 2; j++)
  14. {
  15. printf("%c ", board[i][j]);
  16. }
  17. printf("\n");
  18. }
  19. }

这个函数执行以下操作:

  1. 打印游戏区域的列号,以便玩家可以根据列号来选择方格。这部分通过一个循环和 printf 函数实现。

  2. 打印游戏区域的状态。在一个嵌套的循环中,它遍历游戏区域的每个方格,读取方格的状态(通常是字符 '0' 表示未揭开,或其他字符表示已揭开),然后使用 printf 打印在终端上。

步骤4:布置雷

为什么需要布置地雷?

地雷的布置是扫雷游戏的核心,因为它确定了游戏的难度和挑战性。在扫雷中,地雷的分布是随机的,玩家需要根据揭开的方格周围地雷的数量来推测地雷的位置,从而逐步揭开方格,避免触发地雷。

地雷的随机分布使每局游戏都有不同的挑战,玩家需要运用逻辑和推理来排查出地雷,同时避免触发它们。地雷的布置也是游戏的可重复性,因为每次游戏都会有不同的地雷分布,从而保持游戏的新鲜感。

通过布置地雷,扫雷游戏变得更加有趣和具有挑战性,让玩家享受探索和决策的乐趣。这是扫雷游戏的核心玩法之一。

布置地雷的函数

在步骤4中,我们实现了名为 SetMine 的函数,用于随机布置地雷。以下是函数的声明和实现:

void SetMine(char board[ROWS][COLS], int row, int col);
  • char board[ROWS][COLS]:这是一个二维字符数组,表示游戏区域的状态,ROWSCOLS 是游戏区域的行数和列数。

函数实现

函数的实现如下:

  1. void SetMine(char board[ROWS][COLS], int row, int col)
  2. {
  3. int count = EASY_COUNT;
  4. while (count)
  5. {
  6. int x = rand() % (row - 2) + 1; // 随机选择行
  7. int y = rand() % (col - 2) + 1; // 随机选择列
  8. if (board[x][y] == '0')
  9. {
  10. board[x][y] = '1'; // 设置为地雷
  11. count--;
  12. }
  13. }
  14. }

这个函数执行以下操作:

  1. 初始化一个计数器 count,用于跟踪要布置的地雷数量。

  2. 使用一个 while 循环来不断尝试随机选择方格,并将其设置为地雷。循环的条件是 count 大于零,表示还有地雷需要布置。

  3. 在每次循环中,使用 rand() 函数随机生成行数 x 和列数 y,这将在游戏区域内选择一个随机方格。我们使用 % (row - 2)% (col - 2) 来确保随机选择的方格位于游戏区域内,而不在外围边界上,因为外围边界通常不包含地雷。

  4. 检查所选择的方格是否已经是地雷,即是否为字符 '0'。如果是空方格,则将其设置为地雷,即字符 '1',并将计数器 count 减一。

  5. 重复上述步骤,直到 count 变为零,表示所有地雷都已经布置完毕。

步骤5:计算周围的地雷数量

我们需要一个函数来计算指定方格周围的地雷数量。为此,在game.c中,我们实现了GetMineCount函数。

为什么需要计算周围地雷数量?

在扫雷游戏中,计算周围地雷数量是为了提供玩家有关已揭开方格周围的地雷信息。这个信息对玩家进行下一步操作非常重要,因为它可以帮助玩家推测周围的方格是否包含地雷,从而决定哪些方格可以安全地揭开。

通过计算周围地雷数量,玩家可以获得重要的提示,例如如果一个方格周围有3颗地雷,那么周围的3个方格可能包含地雷。这有助于玩家进行推理和策略,以最小化触发地雷的风险,同时逐步排查出非地雷的方格。

计算周围地雷数量是扫雷游戏的核心逻辑之一,它提供了重要的游戏信息,帮助玩家进行决策,使游戏更加具有挑战性。

计算周围地雷数量的函数

在本步骤中,我们实现了名为 GetMineCount 的函数,用于计算指定方格周围的地雷数量。以下是函数的声明和实现:

int GetMineCount(char mine[ROWS][COLS], int x, int y);
  • char mine[ROWS][COLS]:这是一个二维字符数组,表示游戏区域内地雷的分布情况。
  • int xint y:这两个参数表示要计算地雷数量的方格的坐标。

函数实现

函数的实现如下:

  1. int GetMineCount(char mine[ROWS][COLS], int x, int y)
  2. {
  3. return mine[x - 1][y] +
  4. mine[x - 1][y - 1] +
  5. mine[x][y - 1] +
  6. mine[x + 1][y - 1] +
  7. mine[x + 1][y] +
  8. mine[x + 1][y + 1] +
  9. mine[x][y + 1] +
  10. mine[x - 1][y + 1] - 8 * '0';
  11. }

这个函数执行以下操作:

  1. 它使用输入的坐标 (x, y) 来确定要计算周围地雷数量的方格。

  2. 在函数内部,它检查方格周围的8个相邻方格,这些方格的坐标相对于当前方格 (x, y) 有一定的规律。这8个相邻方格的坐标是 (x - 1, y)(x - 1, y - 1)(x, y - 1)(x + 1, y - 1)(x + 1, y)(x + 1, y + 1)(x, y + 1)(x - 1, y + 1)

  3. 对每个相邻方格,它检查 mine 数组中的值,如果该方格包含地雷,对应的值是字符 '1',否则是字符 '0'。函数将这些值相加,然后减去 8 倍的字符 '0'(即 8),以得到周围地雷的总数。

  4. 最后,函数返回周围地雷的数量,这个数字将用于在已揭开的方格上显示周围的地雷数量。

步骤6:扫雷

通过扫雷操作,玩家可以:

  • 揭开方格并查找地雷。
  • 使用周围地雷数量的信息来决定下一步的操作。
  • 推测地雷的位置,从而避免触发地雷。
  • 逐步解锁整个游戏区域,直到游戏结束。
  • 享受扫雷游戏的策略性和推理性质。

扫雷操作的函数

在步骤6中,我们实现了名为 FindMine 的函数,用于处理玩家的扫雷操作。以下是函数的声明和实现:

void FindMine(char mine[ROWS][COLS], char show[ROWS][COLS], int row, int col);
  • char mine[ROWS][COLS]:这是一个二维字符数组,表示游戏区域内地雷的分布情况。
  • char show[ROWS][COLS]:这也是一个二维字符数组,用于存储已排查出的方格的信息。
  • int rowint col:这两个参数表示游戏区域的行数和列数。

函数实现

函数的实现如下:

  1. void FindMine(char mine[ROWS][COLS], char show[ROWS][COLS], int row, int col)
  2. {
  3. int x = 0; // 用于存储玩家输入的 x 坐标
  4. int y = 0; // 用于存储玩家输入的 y 坐标
  5. int win = 0; // 用于记录已排查出的方格数量
  6. // 只要玩家没有排查出所有非地雷的方格,继续循环
  7. while (win < (row - 2) * (col - 2) - EASY_COUNT)
  8. {
  9. printf("请输入排查雷的坐标:");
  10. scanf("%d%d", &x, &y);
  11. if (x >= 1 && x <= row && y >= 1 && y <= col)
  12. {
  13. if (mine[x][y] == '1')
  14. {
  15. printf("很遗憾,你被炸死了\n");
  16. DisplayBoard(mine, ROWS, COLS); // 显示整个游戏区域的地雷分布
  17. break; // 游戏结束
  18. }
  19. else
  20. {
  21. int count = GetMineCount(mine, x, y); // 计算周围地雷数量
  22. show[x][y] = count + '0'; // 更新 show 数组,显示周围地雷数量
  23. DisplayBoard(show, row, col); // 显示更新后的游戏区域状态
  24. win++; // 已排查出的方格数量加一
  25. }
  26. }
  27. else
  28. {
  29. printf("输入坐标非法,请重新输入\n");
  30. }
  31. }
  32. if (win == (row - 2) * (col - 2) - EASY_COUNT)
  33. {
  34. printf("恭喜你,排雷成功\n");
  35. DisplayBoard(mine, row, col); // 显示整个游戏区域的地雷分布
  36. }
  37. }

这个函数执行以下操作:

  1. 定义变量 xy,用于接收玩家输入的坐标,以及 win 用于跟踪已排查出的方格数量。

  2. 使用一个 while 循环,只要玩家没有排查出所有非地雷的方格,就会继续执行。win 表示已排查出的方格数量,如果等于 (row - 2) * (col - 2) - EASY_COUNT,则表示所有非地雷方格都已排查出。

  3. 在每次循环中,程序要求玩家输入要排查的方格坐标,即 xy

  4. 检查输入的坐标是否合法,即是否在游戏区域内。如果坐标合法,继续执行。

  5. 如果玩家选择的方格包含地雷(mine[x][y] == '1'),则游戏失败,程序输出信息并显示整个游戏区域的地雷分布。游戏结束。

  6. 如果玩家选择的方格不包含地雷,程序会计算并显示该方格周围的地雷数量(使用 GetMineCount 函数),然后更新 show 数组来显示这个数量,并递增 win

  7. 重复这个过程,直到玩家排查出所有非地雷的方格或者触发地雷结束游戏。

  8. 如果 win 等于 (row - 2) * (col - 2) - EASY_COUNT,表示玩家成功排查出所有非地雷的方格,游戏胜利。程序输出相应信息,并显示整个游戏区域的地雷分布。

步骤7:游戏主函数

test.c中,我们编写了游戏的主函数。该函数允许玩家选择开始游戏或退出,并在游戏过程中调用上述函数来控制游戏流程。

函数实现

  1. int main()
  2. {
  3. int input = 0;
  4. srand((unsigned int)time(NULL)); // 随机数种子初始化,以使随机数生成更具随机性
  5. do
  6. {
  7. menu(); // 显示游戏菜单
  8. printf("请选择:");
  9. scanf("%d", &input);
  10. switch (input)
  11. {
  12. case 1:
  13. printf("游戏开始\n");
  14. game(); // 调用游戏函数,开始游戏
  15. break;
  16. case 0:
  17. printf("游戏结束\n");
  18. break;
  19. default:
  20. printf("选择错误,请重新选择\n");
  21. break;
  22. }
  23. } while (input);
  24. return 0;
  25. }

  1. int input = 0;:在主函数中,我们首先定义一个整数变量 input,用于接收玩家的菜单选择。

  2. srand((unsigned int)time(NULL));:这行代码用于初始化随机数生成器。它基于当前时间,以确保每次游戏都具有不同的随机性。这是因为随机数生成器的种子通常以时间为基础,以生成不同的随机数序列。

  3. do 循环:游戏的主循环开始。这是一个无限循环,直到玩家选择退出游戏(输入0)。

  4. menu();:在每次循环开始时,调用 menu 函数,显示游戏菜单。玩家可以选择开始游戏(输入1)或退出游戏(输入0)。

  5. printf("请选择:");scanf("%d", &input);:提示玩家选择,并接收玩家输入的选择,将其存储在 input 变量中。

  6. switch (input):使用 switch 语句根据玩家的选择执行不同的操作。

    • 如果玩家选择1(开始游戏),则执行 game() 函数,开始扫雷游戏。

    • 如果玩家选择0(退出游戏),则输出相关信息,并结束游戏。

    • 如果玩家输入其他任何数字,表示选择错误,会输出错误信息并继续等待玩家的选择。

  7. 游戏主循环在 do-while 结构中,因此会一直运行,直到玩家选择退出游戏(输入0)。

  8. 当游戏结束后,主函数返回0,游戏结束。

这一步是整个扫雷游戏的控制中心,它确保游戏在菜单选择和游戏操作之间循环进行,允许玩家在需要时启动新游戏或退出游戏。

合三为一,扫雷启动!

为什么要分三块?

将整个游戏分为 game.hgame.ctest.c 三个文件有以下好处:

  1. 模块化和可读性:将代码分成模块,每个模块负责不同的任务或功能。这提高了代码的可读性,使每个部分都容易理解,不必混杂在一起。

  2. 重点突出:每个文件的介绍和代码段可以重点突出该文件的功能,而不会让读者在整个代码库中迷失方向。

  3. 更易于维护:在将代码分成模块后,维护和更新代码将更加容易,因为每个文件都有清晰的职责。

game.h - 游戏头文件

game.h 文件是扫雷游戏的头文件,它包含了游戏中使用的数据结构、函数声明以及一些常量的定义。这个文件在整个游戏中起着重要的桥梁作用,用于引入和声明游戏所需的元素。

作用和功能: game.h 定义了扫雷游戏的数据结构和函数声明,包括初始化棋盘、显示棋盘、布置地雷、计算周围地雷数量和执行扫雷操作。它为其他部分提供了必要的接口和工具。

  1. #pragma once
  2. #include <stdio.h>
  3. #include <windows.h>
  4. #include <time.h>
  5. #include <stdlib.h>
  6. #define ROW 9
  7. #define COL 9
  8. #define ROWS ROW+2
  9. #define COLS COL+2
  10. #define EASY_COUNT 10
  11. void InitBoard(char board[ROWS][COLS], int rows, int cols, char set);//初始化棋盘
  12. void DisplayBoard(char board[ROWS][COLS], int row, int col);//打印棋盘
  13. void SetMine(char board[ROWS][COLS], int row, int col);//布置雷
  14. void FindMine(char mine[ROWS][COLS], char show[ROWS][COLS], int row, int col);//扫雷

game.c - 游戏功能实现

game.c 文件包含了扫雷游戏的核心功能实现,包括初始化棋盘、布置地雷、计算周围地雷数量以及执行扫雷操作。这是游戏的引擎部分,负责处理游戏逻辑。

作用和功能: game.c 实现了扫雷游戏的核心功能,包括初始化游戏板、布置地雷、计算周围地雷数量以及执行扫雷操作。

  1. #define _CRT_SECURE_NO_WARNINGS 1
  2. #include "game.h"//引用头文件
  3. //初始化棋盘
  4. void InitBoard(char board[ROWS][COLS], int rows, int cols, char set)
  5. {
  6. int i = 0;
  7. int j = 0;
  8. for (i = 0; i < rows; i++)//行
  9. {
  10. for (j = 0; j < cols; j++)//列
  11. {
  12. board[i][j] = set;
  13. }
  14. }
  15. }
  16. //打印棋盘
  17. void DisplayBoard(char board[ROWS][COLS], int row, int col)
  18. {
  19. int i = 0;
  20. int j = 0;
  21. printf(" ");
  22. for (i = 1; i <= col - 2; i++)
  23. {
  24. printf("%d ", i);
  25. }
  26. printf("\n");
  27. for (i = 1; i <= row - 2; i++)
  28. {
  29. printf("%d ", i);
  30. for (j = 1; j <= col - 2; j++)
  31. {
  32. printf("%c ", board[i][j]);
  33. }
  34. printf("\n");
  35. }
  36. }
  37. //布置雷
  38. void SetMine(char board[ROWS][COLS], int row, int col)
  39. {
  40. int count = EASY_COUNT;
  41. while (count)
  42. {
  43. int x = rand() % (row - 2) + 1;//1-9
  44. int y = rand() % (col - 2) + 1;//1-9
  45. if (board[x][y] == '0')
  46. {
  47. board[x][y] = '1';
  48. count--;
  49. }
  50. }
  51. }
  52. //计算x,y坐标周围有几个雷
  53. int GetMineCount(char mine[ROWS][COLS], int x, int y)
  54. {
  55. return mine[x - 1][y] +
  56. mine[x - 1][y - 1] +
  57. mine[x][y - 1] +
  58. mine[x + 1][y - 1] +
  59. mine[x + 1][y] +
  60. mine[x + 1][y + 1] +
  61. mine[x][y + 1] +
  62. mine[x - 1][y + 1] - 8 * '0';
  63. }
  64. //扫雷
  65. void FindMine(char mine[ROWS][COLS], char show[ROWS][COLS], int row, int col)
  66. {
  67. int x = 0;
  68. int y = 0;
  69. int win = 0;
  70. while (win < (row-2) * (col-2) - EASY_COUNT)
  71. {
  72. printf("请输入排查雷的坐标:");
  73. scanf("%d%d", &x, &y);
  74. if (x >= 1 && x <= row && y >= 1 && y <= col)
  75. {
  76. //坐标合法
  77. //1.踩雷
  78. if (mine[x][y] == '1')
  79. {
  80. printf("很遗憾,你被炸死了\n");
  81. DisplayBoard(mine, ROWS, COLS);
  82. break;
  83. }
  84. else//2.不是雷
  85. {
  86. //计算x,y坐标周围有几个雷
  87. int count = GetMineCount(mine, x, y);
  88. show[x][y] = count + '0';
  89. DisplayBoard(show, row, col);
  90. win++;
  91. }
  92. }
  93. else
  94. {
  95. printf("输入坐标非法,请重新输入\n");
  96. }
  97. }
  98. if (win == (row-2) * (col-2) - EASY_COUNT)
  99. {
  100. printf("恭喜你,排雷成功\n");
  101. DisplayBoard(mine, row, col);
  102. }
  103. }

test.c - 游戏测试和主程序

test.c 文件包含了游戏的主程序,它负责控制游戏的整个流程,包括菜单、游戏的开始和结束。这是与用户交互的部分,也是整个游戏的入口点。

作用和功能: test.c 包含了游戏的主程序,控制游戏的流程,包括菜单的显示、游戏的开始和结束。它是整个游戏的入口点。

  1. #define _CRT_SECURE_NO_WARNINGS 1
  2. //扫雷游戏测试代码
  3. #include "game.h"//引用头文件
  4. void menu()
  5. {
  6. printf("*************************************\n");
  7. printf("********** 1. play 0. exit *********\n");
  8. printf("*************************************\n");
  9. }
  10. void game()
  11. {
  12. char mine[ROWS][COLS] = { 0 };//存放雷的信息
  13. char show[ROWS][COLS] = { 0 };//存放排查出的雷的信息
  14. //初始化棋盘
  15. InitBoard(mine, ROWS, COLS, '0');
  16. InitBoard(show, ROWS, COLS, '*');
  17. //打印棋盘
  18. DisplayBoard(show, ROWS, COLS);
  19. //布置雷
  20. SetMine(mine, ROWS, COLS);
  21. //DisplayBoard(mine, ROWS, COLS);//仅供测试用
  22. //扫雷
  23. FindMine(mine, show, ROWS, COLS);
  24. }
  25. int main()
  26. {
  27. int input = 0;
  28. srand((unsigned int)time(NULL));//随机数种子
  29. do
  30. {
  31. menu();
  32. printf("请选择:");
  33. scanf("%d", &input);
  34. switch (input)
  35. {
  36. case 1:
  37. printf("游戏开始\n");
  38. game();
  39. break;
  40. case 0:
  41. printf("游戏结束\n");
  42. break;
  43. default:
  44. printf("选择错误,请重新选择\n");
  45. break;
  46. }
  47. } while (input);
  48. return 0;
  49. }

 实践测试

下面是我亲自实践的例子:

请注意:为了简化起见,我把game.h头文件中ROW与COL的值均改为3,EASY_COUNT(雷数)改成5,并且在test.c文件中加入了

DisplayBoard(mine, ROWS, COLS);//仅供测试用

在这里:

  1. void game()
  2. {
  3. char mine[ROWS][COLS] = { 0 };//存放雷的信息
  4. char show[ROWS][COLS] = { 0 };//存放排查出的雷的信息
  5. //初始化棋盘
  6. InitBoard(mine, ROWS, COLS, '0');
  7. InitBoard(show, ROWS, COLS, '*');
  8. //打印棋盘
  9. DisplayBoard(show, ROWS, COLS);
  10. //布置雷
  11. SetMine(mine, ROWS, COLS);
  12. DisplayBoard(mine, ROWS, COLS);//在这里哦!
  13. //扫雷
  14. FindMine(mine, show, ROWS, COLS);
  15. }

导致游戏开始时出现了雷的分布图(开挂一般的存在)

实际操作中,玩家也可以自行修改ROW,COL和EASY_COUNT的值,以改变扫雷游戏的难度。

结语与展望

扫雷游戏是一款经典的益智游戏,通过实际编写并介绍了其实现过程,我们希望读者对如何创建简单的控制台游戏有了更深入的了解。但是,代码的完善是一个永无止境的过程,许多不足是难以避免的,还望读者体谅。

首先,这个示例中的代码是一个基础版本,仅包括了扫雷游戏的核心功能。可以进一步改进并添加更多功能,如计时器、难度选择、排行榜等,以增强游戏体验。

其次,代码结构可以更模块化和清晰。将不同功能的代码分成更小的函数和文件,可以提高代码的可维护性和可读性。

此外,代码中的注释和文档可以更详尽,以帮助其他开发者理解和使用代码。

总之,这个示例代码是一个入门级别的扫雷游戏,有很多改进和扩展的空间。编写代码是一个不断学习和改进的过程,希望读者可以在此基础上继续发展和完善自己的游戏项目。

谢谢阅读本博客,希望它对您有所帮助,鼓励您不断学习和提高编程技能,创造更多有趣的应用程序。

本人是C语言小白一枚,若想提高编写扫雷程序的质量(如生成分隔线,提高生成雷的效率、自动清屏,像原版扫雷一样实现“0”的扩散等等),可以参考大佬@li_zi_jin的博文,经本人许可,我将博客网址粘贴如下:

C语言怎样写扫雷-CSDN博客

声明:本文内容由网友自发贡献,转载请注明出处:【wpsshop博客】
推荐阅读
相关标签
  

闽ICP备14008679号