经验首页 前端设计 程序设计 Java相关 移动开发 数据库/运维 软件/图像 大数据/云计算 其他经验
当前位置:技术经验 » 程序设计 » C 语言 » 查看文章
基于C语言实现简单扫雷游戏
来源:jb51  时间:2021/11/15 17:22:16  对本文有异议

在每一个电脑里总有一个固定的小游戏-扫雷,那今天就让我们一起来实现下扫雷。

1.主函数的构建

  1. int main()
  2. {
  3. int input = 0;
  4. do
  5. {
  6. menu();
  7. printf("请选择是否开始游戏(1/0):>");
  8. scanf("%d", &input);
  9. switch (input)
  10. {
  11. case 1:
  12. game();
  13. break;
  14. case 0:
  15. printf("游戏退出!");
  16. break;
  17. default:
  18. printf("输入错误!请重新输入:");
  19. break;
  20. }
  21. } while (input);
  22. return 0;
  23. }

创建主函数和菜单,并对此进行游戏选择判断。

2.雷盘的设计

  1. char mine[ROWS][COLS]; //扫雷数组
  2. char show[ROWS][COLS]; //展示数组
  3. InitMine(mine, ROWS, COLS,'0'); //初始化的雷盘
  4. InitShow(show, ROW, COL,'*'); //初始化展示的雷盘

这里我们创建两个二维数组,mine数组用来布置雷,show数组用来展示雷盘情况。

InitMine函数实现如下:

  1. void InitMine(char mine[ROWS][COLS], int row, int col) // 初始化雷盘
  2. {
  3. int i = 0;
  4. int j = 0;
  5. for (i = 0; i < row; i++)
  6. {
  7. for (j = 0; j < col; j++)
  8. {
  9. mine[i][j] = '0';
  10. }
  11. }
  12. }

接下来我们需要展示雷盘,可我们不会把将布置雷的雷盘展示出去,这时我们用到了show函数来帮助我们实现这一需求。

InitShow函数实现如下:

  1. void InitShow(char show[ROWS][COLS], int row, int col,char set) //初始化展示的雷盘
  2. {
  3. int i = 0;
  4. int j = 0;
  5. for (i = 1; i <= row; i++)
  6. {
  7. for (j = 1; j <= col; j++)
  8. {
  9. show[i][j] = set;
  10. }
  11. }
  12. }

这样我们就完成了第一步的设计。

3.布置雷

在完成雷盘之后,我们需要在我们的雷盘上布置雷,那这里我们引入了新的函数-SetMine,将雷布置在Mine数组中。

函数实现如下:

  1. void SetMine(char mine[ROWS][COLS], int row, int col, int count) // 随机布雷
  2. {
  3. while (count)//雷的个数
  4. {
  5. int x = rand() % row + 1;//(1-9)
  6. int y = rand() % col + 1;//(1-9)
  7. mine[x][y] = '1';
  8. count--;
  9. }
  10. }

这里我们又又又遇见了rand函数,那我们则需要设置一个随机器-srand() ,别忘了它的头文件是<stdlib.h>,我们应该把srand()放在do whie中,不然雷会一直变动。

如图:

  1. int main()
  2. {
  3. int input = 0;
  4. do
  5. {
  6. menu();
  7. srand((unsigned int)time(NULL)); //产生随机数
  8. printf("请选择是否开始游戏(1/0):>");
  9. scanf("%d", &input);
  10. switch (input)
  11. {
  12. case 1:
  13. game();
  14. break;
  15. case 0:
  16. printf("游戏退出!");
  17. break;
  18. default:
  19. printf("输入错误!请重新输入:");
  20. break;
  21. }
  22. } while (input);
  23. return 0;
  24. }

4.打印雷盘

这里我们使用DisplayBoard函数来打印雷盘

函数实现如下:

  1. void DisplayBoard(char arr[ROWS][COLS], int row, int col) // 打印展示雷盘
  2. {
  3. int i = 0;
  4. int j = 0;
  5. printf(" ");
  6. for (i = 0; i <= row; i++)//打印列号
  7. {
  8. printf("%d ", i);
  9. }
  10. printf("\n");
  11. for (i = 1; i <= row; i++)
  12. {
  13. printf("%2d", i);//打印行号
  14. for (j = 1; j <= col; j++)
  15. {
  16. printf(" %c", arr[i][j]);
  17. }
  18. printf("\n");
  19. }
  20. }

5.开始排雷

这里我们创建PlayGame函数来进行我们一系列的操作

函数实现如下:

  1. void PlayGame(char mine[ROWS][COLS], char show[ROWS][COLS])
  2. {
  3. int x = 0;
  4. int y = 0;
  5. int win = 0;//统计排雷的个数
  6. int count = 0;//统计周围雷的个数
  7. while (win < ROW * COL - COUNT)//判断条件
  8. {
  9. printf("请输入坐标:>");
  10. scanf("%d %d", &x, &y);
  11. if (show[x][y] == count + '0'|| show[x][y] == ' ')//避免重复排雷
  12. {
  13. printf("此处已经排过雷\n");
  14. }
  15. if (x >= 1 && x <= ROW && y >= 1 && y <= COL)//输入坐标是否合法
  16. {
  17. if (mine[x][y] == '1')
  18. {
  19. printf("很遗憾,你被炸死了\n");
  20. DisplayBoard(mine, ROW, COL);
  21. break;//退出循环
  22. }
  23. else
  24. {
  25. count = FindMineCount(mine, x, y);
  26. if (count == 0)//满足展开的条件
  27. {
  28. show[x][y] = ' ';
  29. expand(mine, x, y, show, &win);
  30. }
  31. else
  32. {
  33. show[x][y] = count + '0';
  34. }
  35. win++;
  36. DisplayBoard(show, ROW, COL);
  37. }
  38. }
  39. else
  40. {
  41. printf("输入坐标不合法\n");
  42. }
  43. }
  44. if (win == ROW * COL - COUNT)//判断排雷结束
  45. {
  46. printf("排雷成功\n");
  47. DisplayBoard(mine, ROW, COL);//打印雷盘中雷的分布
  48. }
  49. }

这里我们引入了FindMineCount函数expand函数

FindMineCount:

  1. static int FindMineCount(char mine[ROWS][COLS], int i, int j) //统计雷的个数
  2. {
  3. return mine[i - 1][j] +
  4. mine[i - 1][j - 1] +
  5. mine[i][j - 1] +
  6. mine[i + 1][j - 1] +
  7. mine[i + 1][j] +
  8. mine[i + 1][j + 1] +
  9. mine[i][j + 1] +
  10. mine[i - 1][j + 1] - 8 * '0';
  11. }

使用这个FindMineCount函数用来查找左边周围雷的个数。

expand函数:

  1. void expand(char mine[ROWS][COLS], int x, int y, char show[ROWS][COLS], int* p)//展开函数
  2. {
  3. int i,j;
  4. for (i = -1; i <=1; i++)
  5. {
  6. for (j = -1; j <=1; j++)
  7. {
  8. if (i != 0 || j != 0)//避免排到自己
  9. {
  10. if (x + i >= 1 && x + i <= ROW && y + j >= 1 && y + j <= COL) //判断x y坐标是否合法
  11. {
  12. if (show[x + i][y + j] == '*' && mine[x + i][y + j] != '1')//防止死递归
  13. {
  14. int count = GetMineCount(mine, x + i, y + j);
  15. if (count != 0)
  16. {
  17. show[x + i][y + j] = count + '0';
  18. (*p)++;//排雷数加一
  19. }
  20. else
  21. {
  22. show[x + i][y + j] = ' ';
  23. (*p)++;//排雷数加一
  24. expand(mine, x + i, y + j, show, p);
  25. }
  26. }
  27. }
  28. }
  29. }
  30. }
  31. }

用此函数来判断是否符合条件进行展开。

对此所有步骤都已写完。

附上头文件、源文件。

game.h 

  1. #define _CRT_SECURE_NO_WARNINGS 1
  2. #include <stdio.h>
  3. #include <stdlib.h>
  4. #define ROW 9 //雷盘操作范围
  5. #define COL 9
  6. #define ROWS ROW+2//雷盘实际大小
  7. #define COLS COL+2
  8. #define COUNT 10 //布置雷的个数
  9. //设置游戏菜单
  10. void menu();
  11. //初始化雷盘
  12. void InitMine(char mine[ROWS][COLS], int row, int col);
  13. //初始化展示的雷盘
  14. void InitShow(char show[ROWS][COLS], int row, int col);
  15. // 随机布雷
  16. void SetMine(char mine[ROWS][COLS], int x, int y, int count);
  17. // 打印展示雷盘
  18. void DisplayBoard(char arr[ROWS][COLS], int row, int col);
  19. //玩游戏
  20. void PlayGame(char mine[ROWS][COLS], char show[ROWS][COLS]);

game.c

  1. #include "game.h"
  2. void menu() //游戏菜单
  3. {
  4. printf("****************************\n");
  5. printf("**** 1.开始游戏 ****\n");
  6. printf("**** 0.退出游戏 ****\n");
  7. printf("****************************\n");
  8. }
  9. void InitMine(char mine[ROWS][COLS], int row, int col,char set) // 初始化雷盘
  10. {
  11. int i = 0;
  12. int j = 0;
  13. for (i = 0; i < row; i++)
  14. {
  15. for (j = 0; j < col; j++)
  16. {
  17. mine[i][j] = set;
  18. }
  19. }
  20. }
  21. void InitShow(char show[ROWS][COLS], int row, int col,char set) //初始化展示的雷盘
  22. {
  23. int i = 0;
  24. int j = 0;
  25. for (i = 1; i <= row; i++)
  26. {
  27. for (j = 1; j <= col; j++)
  28. {
  29. show[i][j] = set;
  30. }
  31. }
  32. }
  33. void SetMine(char mine[ROWS][COLS], int row, int col, int count) // 随机布雷
  34. {
  35. while (count)//雷的个数
  36. {
  37. int x = rand() % row + 1;//(1-9)
  38. int y = rand() % col + 1;//(1-9)
  39. mine[x][y] = '1';
  40. count--;
  41. }
  42. }
  43. void DisplayBoard(char arr[ROWS][COLS], int row, int col) // 打印展示雷盘
  44. {
  45. int i = 0;
  46. int j = 0;
  47. printf(" ");
  48. for (i = 0; i <= row; i++)
  49. {
  50. printf("%d ", i);
  51. }
  52. printf("\n");
  53. for (i = 1; i <= row; i++)
  54. {
  55. printf("%2d", i);
  56. for (j = 1; j <= col; j++)
  57. {
  58. printf(" %c", arr[i][j]);
  59. }
  60. printf("\n");
  61. }
  62. }
  63. static int GetMineCount(char mine[ROWS][COLS], int i, int j) //统计雷的个数
  64. {
  65. return mine[i - 1][j] +
  66. mine[i - 1][j - 1] +
  67. mine[i][j - 1] +
  68. mine[i + 1][j - 1] +
  69. mine[i + 1][j] +
  70. mine[i + 1][j + 1] +
  71. mine[i][j + 1] +
  72. mine[i - 1][j + 1] - 8 * '0';
  73. }
  74. void expand(char mine[ROWS][COLS], int x, int y, char show[ROWS][COLS], int* p)//展开函数
  75. {
  76. int i,j;
  77. for (i = -1; i <=1; i++)
  78. {
  79. for (j = -1; j <=1; j++)
  80. {
  81. if (i != 0 || j != 0)//避免排到自己
  82. {
  83. if (x + i >= 1 && x + i <= ROW && y + j >= 1 && y + j <= COL) //判断x y坐标是否合法
  84. {
  85. if (show[x + i][y + j] == '*' && mine[x + i][y + j] != '1')//防止死递归
  86. {
  87. int count = GetMineCount(mine, x + i, y + j);
  88. if (count != 0)
  89. {
  90. show[x + i][y + j] = count + '0';
  91. (*p)++;//排雷数加一
  92. }
  93. else
  94. {
  95. show[x + i][y + j] = ' ';
  96. (*p)++;//排雷数加一
  97. expand(mine, x + i, y + j, show, p);
  98. }
  99. }
  100. }
  101. }
  102. }
  103. }
  104. }
  105. // 主逻辑
  106. void PlayGame(char mine[ROWS][COLS], char show[ROWS][COLS])
  107. {
  108. int x = 0;
  109. int y = 0;
  110. int win = 0;//统计排雷的个数
  111. int count = 0;// 统计雷的个数
  112. while (win < ROW * COL - COUNT)//判断条件
  113. {
  114. printf("请输入坐标:>");
  115. scanf("%d %d", &x, &y);
  116. if (show[x][y] == count + '0'|| show[x][y] == ' ')//避免重复排雷
  117. {
  118. printf("已经排过雷\n");
  119. }
  120. if (x >= 1 && x <= ROW && y >= 1 && y <= COL)//输入坐标是否合法
  121. {
  122. if (mine[x][y] == '1')
  123. {
  124. printf("很遗憾,你被炸死了\n");
  125. DisplayBoard(mine, ROW, COL);
  126. break;
  127. }
  128. else
  129. {
  130. count = GetMineCount(mine, x, y);
  131. if (count == 0)
  132. {
  133. show[x][y] = ' ';
  134. expand(mine, x, y, show, &win);
  135. }
  136. else
  137. {
  138. show[x][y] = count + '0';
  139. }
  140. win++;
  141. DisplayBoard(show, ROW, COL);
  142. }
  143. }
  144. else
  145. {
  146. printf("输入坐标不合法\n");
  147. }
  148. }
  149. if (win == ROW * COL - COUNT)//判断排雷结束
  150. {
  151. printf("排雷成功\n");
  152. DisplayBoard(mine, ROW, COL);
  153. }
  154. }

text.c

  1. #include "game.h"
  2. void game()
  3. {
  4. char mine[ROWS][COLS]; //扫雷数组
  5. char show[ROWS][COLS]; //展示数组
  6. InitMine(mine, ROWS, COLS,'0'); //初始化的雷盘
  7. InitShow(show, ROW, COL,'*'); //初始化展示的雷盘
  8. SetMine(mine, ROW, COL, COUNT); //随机布雷
  9. DisplayBoard(show, ROW, COL); //打印雷盘
  10. PlayGame(mine, show); //玩游戏
  11. }
  12. int main()
  13. {
  14. int input = 0;
  15. srand((unsigned int)time(NULL)); //产生随机数
  16. do
  17. {
  18. menu();
  19. printf("请选择是否开始游戏(1/0):>");
  20. scanf("%d", &input);
  21. switch (input)
  22. {
  23. case 1:
  24. game();
  25. break;
  26. case 0:
  27. printf("游戏退出!");
  28. break;
  29. default:
  30. printf("输入错误!请重新输入:");
  31. break;
  32. }
  33. } while (input);
  34. return 0;
  35. }

谢谢观看!

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持w3xue。

 友情链接:直通硅谷  点职佳  北美留学生论坛

本站QQ群:前端 618073944 | Java 606181507 | Python 626812652 | C/C++ 612253063 | 微信 634508462 | 苹果 692586424 | C#/.net 182808419 | PHP 305140648 | 运维 608723728

W3xue 的所有内容仅供测试,对任何法律问题及风险不承担任何责任。通过使用本站内容随之而来的风险与本站无关。
关于我们  |  意见建议  |  捐助我们  |  报错有奖  |  广告合作、友情链接(目前9元/月)请联系QQ:27243702 沸活量
皖ICP备17017327号-2 皖公网安备34020702000426号