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

本文实例为大家分享了C语言实现扫雷游戏的具体代码,供大家参考,具体内容如下

一、游戏介绍

扫雷游戏是在一个指定的二维空间里,随机布置雷,把不是雷的位置都找出来,在你点一个位置的时候它会显示它周围全部雷的个数,根据这个线索去找 ,会更容易赢。

二、实现模块

文件名                作用
clear_mine.h      三子棋的函数声明,头文件声明等
clear_mine.c      三子棋函数接口的实现
main.c               三子棋函数测试功能

三、实现原理

1、用两个2维数组保存扫雷信息,一个用来设置雷,另一个用来展示看不见的雷,并把周围的雷的个数统计出来展示。
2、也就是当在排查雷输入坐标的时候要使用这个两个数组,这个坐标位置在设置雷的数组里面如果不是雷,就统计它周围雷个数放在另一个数组里面进行显示。直到我们排查排查 ROW乘COL-雷个数次,即可胜利
3、这里面最重要的怎样在方格位置上是显示个数,用字符是最方便的,不是雷的初始化为字符0,是雷放字符置为1。当一个位置上不是雷把他周围8个的字符加起来-去8*字符0就是有多少个雷的个数。再把雷的个数转化为字符放在可视化数字里面显示,只需要个数加上字符0即可。

四、实现逻辑

(一)、创建menu菜单函数

  1. void menu()
  2. {
  3. ?? ?printf("########### ?1、游戏开始 ##########\n");
  4. ?? ?printf("########### ?2、退出 ? ##############\n");
  5. }

(二)、用switch语句去创建game游戏开始函数和退出功能

  1. void game()
  2. {
  3. ?? ?//用2个棋盘即两个2维数组,一个进行放雷另一个进行展示棋盘信息
  4. ?? ?char mine[ROWS][COLS] = { 0 };
  5. ?? ?char show[ROWS][COLS] = { 0 };
  6. ?? ?Init(mine,ROWS,COLS,'0');//先把放雷的数组初始化为字符0
  7. ?? ?Init(show,ROWS, COLS, '*');//再把棋盘信息初始化为字符*
  8. ?? ?set_mine(mine, ROW, COL );//放置雷
  9. ?? ?show1(show, ROW, COL);//展示棋盘信息
  10. ?? ?clear_mine(mine, show, ROW, COL);//排查雷
  11. }
  12. int main()
  13. {
  14. ?? ?int insert = 0;
  15. ?? ?srand((unsigned int)time(NULL));
  16. ?? ?do{
  17. ?? ??? ?menu();
  18. ?? ??? ?printf("请选择:");
  19. ?? ??? ?scanf("%d", &insert);
  20. ?? ??? ?switch (insert)
  21. ?? ??? ?{
  22. ?? ??? ?case 1:
  23. ?? ??? ??? ?game();
  24. ?? ??? ??? ?break;
  25. ?? ??? ?case 2:
  26. ?? ??? ??? ?printf("退出游戏");
  27. ?? ??? ??? ?break;
  28. ?? ??? ?default:
  29. ?? ??? ??? ?printf("请重新输入");
  30. ?? ??? ??? ?break;
  31. ?? ??? ?}
  32.  
  33. ?? ?} while (insert);
  34. }

(三)、在void game()函数里面创建上层调用框架

(1)、初始化棋盘并可视化棋盘

1、创建两个数组一个mine数组,一个是show数组并初始化,把它们分别置为字符0和字符*。然后创建一个打印棋盘函数以便呈现我们眼前。我们先调用Init和show1函数来看一下打印效果。
2、需要注意的是我们用二维数组打印两个棋盘,我们就是要打印9x9的棋盘?答案不是,因为我们在设计算法时需要统计坐标周围8个方位的个数,假如要统计边界周围雷的个数,那么就会有数组越界的问题,那么我们就需要在9×9的基础上加2,这些元素我们不打印,心里有数就行。

  1. void Init(char a[][COLS], int rows, int cols, char set)
  2. {
  3. ?? ?int i = 0;
  4. ?? ?int j = 0;
  5. ?? ?for(i = 0; i < rows; i++)
  6. ?? ?{
  7. ?? ??? ?for (j = 0; j < cols; j++)
  8. ?? ??? ?{
  9. ?? ??? ??? ?a[i][j] = set;
  10. ?? ??? ?}
  11. ?? ?}
  12. }
  13. void show1(char a[][COLS], int row, int col)
  14. {
  15. ?? ?int i = 0;
  16. ?? ?int j = 0;
  17. ?? ?for (j = 0; j <col+1; j++)
  18. ?? ?{
  19. ?? ??? ?printf("%d ", j);
  20. ?? ?}
  21. ?? ?printf("\n");
  22. ?? ?for (i = 1; i < row+1; i++)
  23. ?? ?{
  24. ?? ??? ?printf("%d ", i);
  25. ?? ??? ?for (j= 1; j <col+1; j++)
  26. ?? ??? ?{
  27. ?? ??? ??? ?printf("%c ", a[i][j]);
  28. ?? ??? ?}
  29. ?? ??? ?printf("\n");
  30. ?? ?}
  31. ;
  32. }

(2)、设置雷

这一步我门要去设置雷,就在刚刚我们初始化的mine数组里面去放随机雷,这个雷我们可以指定大小 我们定义宏,以便可以方便改。当然我们要现在测试函数main里面设置一个随机数生成器。然后再set_mine函数设置rand函数生成随机坐标。我们雷置为字符1,以便我更好计算。如图代码:

  1. void set_mine(char mine[][COLS], int row, int col)
  2. {
  3. ?? ?int i = 0;
  4. ?? ?int j = 0;
  5. ?? ?int x = 0;
  6. ?? ?int y = 0;
  7. ?? ?int count = mine_count;//雷的个数
  8. ?? ?while (count)
  9. ?? ?{
  10. ?? ??? ?x = rand() % row + 1;//生成一到0的数
  11. ?? ??? ?y = rand() % col + 1;
  12. ?? ??? ?if (mine[x][y] == '0')
  13. ?? ??? ?{
  14. ?? ??? ??? ?mine[x][y] = '1';
  15. ?? ??? ??? ?count--;
  16. ?? ??? ?}
  17. ?? ?}
  18. ?? ??? ?
  19. }

(3)、展示棋盘信息

展示棋盘信息是刚才我们初始化的show函数里面 放的都是字符*,在这里就调用一次来开始玩游戏,进行第一次扫雷。
如图效果:

(4)、排查雷

1、这一步是游戏的核心,进行排查雷,要输入坐标就要先考虑它的合法性。
2、要要考虑他是否被排查过 也就是去重性。
3、在进行判断这个坐标在mine数组里面是否是字符1,如果是游戏结束,反之则把他周围的雷数统计出来给show数组,再调用show1来显示。
4、最一步判断排雷是否成功,只要排了ROW*COL-雷个数次,说明排雷成功。

  1. void clear_mine(char ?mine[][COLS], char show[][COLS], int row, int col)
  2. {
  3. ?? ?int x = 0;
  4. ?? ?int y = 0;
  5. ?? ?int count = 0;
  6. ?? ?while (count = row*col - mine_count)
  7. ?? ?{
  8. ?? ??? ?printf("请输入坐标:");
  9. ?? ??? ?scanf("%d %d", &x, &y);
  10. ?? ??? ?if (x >= 1&& x <= row && y >= 1 && y <= col)
  11. ?? ??? ?{
  12. ?? ??? ??? ?if (show[x][y] == '*')
  13. ?? ??? ??? ?{
  14. ?? ??? ??? ??? ?if (mine[x][y] != '1')
  15. ?? ??? ??? ??? ?{
  16. ?? ??? ??? ??? ??? ?int count1 = 0;
  17. ?? ??? ??? ??? ??? ?count1 = round_mineCount(mine, x, y);
  18. ?? ??? ??? ??? ??? ?show[x][y] = count1 + '0';
  19. ?? ??? ??? ??? ??? ?show1(show, row, col);
  20. ?? ??? ??? ??? ??? ?count--;
  21. ?? ??? ??? ??? ?}
  22. ?? ??? ??? ??? ?else
  23. ?? ??? ??? ??? ?{
  24. ?? ??? ??? ??? ??? ?printf("踩到雷,游戏结束\n");
  25. ?? ??? ??? ??? ??? ?show1(mine, row, col);
  26. ?? ??? ??? ??? ??? ?break;
  27. ?? ??? ??? ??? ?}
  28. ?? ??? ??? ?}
  29. ?? ??? ??? ?else
  30. ?? ??? ??? ?{
  31. ?? ??? ??? ??? ?printf("已经被排查\n");
  32. ?? ??? ??? ?}
  33. ?? ??? ?}
  34. ?? ??? ?else
  35. ?? ??? ?{
  36. ?? ??? ??? ?printf("坐标非法,请重新输入\n");
  37. ?? ??? ?}
  38. ?? ??? ?if (count == 0)
  39. ?? ??? ?{
  40. ?? ??? ??? ?printf("排雷成功");
  41. ?? ??? ??? ?show1(mine, row, col);
  42. ?? ??? ?}
  43. ?? ?}
  44. }
  45. //t统计雷的个数,八个方向
  46. int round_mineCount(char mine[][COLS],int x,int y)
  47. {
  48. ?? ?return ?( mine[x - 1][y] + mine[x + 1][y] +
  49. ?? ??? ?mine[x][y - 1] + mine[x][y + 1] +
  50. ?? ??? ?mine[x - 1][y - 1] + mine[x - 1][y + 1]
  51. ?? ??? ?+ mine[x + 1][y - 1] + mine[x + 1][y + 1]-8*'0');
  52. }

五、全部代码

main.c

  1. #include"clear_mine.h"
  2. void menu()
  3. {
  4. ?? ?printf("########### ?1、游戏开始 ##########\n");
  5. ?? ?printf("########### ?2、退出 ? ##############\n");
  6. }
  7. void game()
  8. {
  9. ?? ?//用2个棋盘即两个2维数组,一个进行放雷另一个进行展示棋盘信息
  10. ?? ?char mine[ROWS][COLS] = { 0 };
  11. ?? ?char show[ROWS][COLS] = { 0 };
  12. ?? ?Init(mine,ROWS,COLS,'0');//先把放雷的数组初始化为字符0
  13. ?? ?Init(show,ROWS, COLS, '*');//再把棋盘信息初始化为字符*
  14. ?? ?set_mine(mine, ROW, COL );//放置雷
  15. ?? ?show1(show, ROW, COL);//展示棋盘信息
  16. ?? ?clear_mine(mine, show, ROW, COL);//排查雷
  17. }
  18. int main()
  19. {
  20. ?? ?int insert = 0;
  21. ?? ?srand((unsigned int)time(NULL));
  22. ?? ?do{
  23. ?? ??? ?menu();
  24. ?? ??? ?printf("请选择:");
  25. ?? ??? ?scanf("%d", &insert);
  26. ?? ??? ?switch (insert)
  27. ?? ??? ?{
  28. ?? ??? ?case 1:
  29. ?? ??? ??? ?game();
  30. ?? ??? ??? ?break;
  31. ?? ??? ?case 2:
  32. ?? ??? ??? ?printf("退出游戏");
  33. ?? ??? ??? ?break;
  34. ?? ??? ?default:
  35. ?? ??? ??? ?printf("请重新输入");
  36. ?? ??? ??? ?break;
  37. ?? ??? ?}
  38.  
  39. ?? ?} while (insert);
  40. }

clear_mine.h

  1. #pragma once
  2. #include<stdio.h>
  3. #include<stdlib.h>
  4. #include<time.h>
  5. #define ROW 9
  6. #define COL 9
  7. #define ROWS ROW+2
  8. #define COLS COL+2
  9. #define mine_count 10//设置雷的个数
  10. #define count2 row*col-Count
  11. void Init(char a[][COLS], int rows,int cols, char set);//初始化棋盘
  12. void set_mine(char mine[][COLS], int row, int col);//设置雷
  13. void show1(char a[][COLS], int row, int col);//展示棋盘信息
  14. void clear_mine(char mine[][COLS], char show[][COLS], int row, int col);// 排查雷
  15. int ?round_mineCount(char mine[][COLS], int row, int col);//统计一个位置周围的雷的个数

clear_mine.c

  1. #include"clear_mine.h"
  2. void Init(char a[][COLS], int rows, int cols, char set)
  3. {
  4. ?? ?int i = 0;
  5. ?? ?int j = 0;
  6. ?? ?for(i = 0; i < rows; i++)
  7. ?? ?{
  8. ?? ??? ?for (j = 0; j < cols; j++)
  9. ?? ??? ?{
  10. ?? ??? ??? ?a[i][j] = set;
  11. ?? ??? ?}
  12. ?? ?}
  13. }
  14. void show1(char a[][COLS], int row, int col)
  15. {
  16. ?? ?int i = 0;
  17. ?? ?int j = 0;
  18. ?? ?for (j = 0; j <col+1; j++)
  19. ?? ?{
  20. ?? ??? ?printf("%d ", j);
  21. ?? ?}
  22. ?? ?printf("\n");
  23. ?? ?for (i = 1; i < row+1; i++)
  24. ?? ?{
  25. ?? ??? ?printf("%d ", i);
  26. ?? ??? ?for (j= 1; j <col+1; j++)
  27. ?? ??? ?{
  28. ?? ??? ??? ?printf("%c ", a[i][j]);
  29. ?? ??? ?}
  30. ?? ??? ?printf("\n");
  31. ?? ?}
  32. ;
  33. }
  34. void set_mine(char mine[][COLS], int row, int col)
  35. {
  36. ?? ?int i = 0;
  37. ?? ?int j = 0;
  38. ?? ?int x = 0;
  39. ?? ?int y = 0;
  40. ?? ?int count = mine_count;
  41. ?? ?while (count)
  42. ?? ?{
  43. ?? ??? ?x = rand() % row + 1;
  44. ?? ??? ?y = rand() % col + 1;
  45. ?? ??? ?if (mine[x][y] == '0')
  46. ?? ??? ?{
  47. ?? ??? ??? ?mine[x][y] = '1';
  48. ?? ??? ??? ?count--;
  49. ?? ??? ?}
  50. ?? ?}
  51. ?? ??? ?
  52. }
  53. void clear_mine(char ?mine[][COLS], char show[][COLS], int row, int col)
  54. {
  55. ?? ?int x = 0;
  56. ?? ?int y = 0;
  57. ?? ?int count = 0;
  58. ?? ?while (count = row*col - mine_count)
  59. ?? ?{
  60. ?? ??? ?printf("请输入坐标:");
  61. ?? ??? ?scanf("%d %d", &x, &y);
  62. ?? ??? ?if (x >= 1&& x <= row && y >= 1 && y <= col)
  63. ?? ??? ?{
  64. ?? ??? ??? ?if (show[x][y] == '*')
  65. ?? ??? ??? ?{
  66. ?? ??? ??? ??? ?if (mine[x][y] != '1')
  67. ?? ??? ??? ??? ?{
  68. ?? ??? ??? ??? ??? ?int count1 = 0;
  69. ?? ??? ??? ??? ??? ?count1 = round_mineCount(mine, x, y);
  70. ?? ??? ??? ??? ??? ?show[x][y] = count1 + '0';
  71. ?? ??? ??? ??? ??? ?show1(show, row, col);
  72. ?? ??? ??? ??? ??? ?count--;
  73. ?? ??? ??? ??? ?}
  74. ?? ??? ??? ??? ?else
  75. ?? ??? ??? ??? ?{
  76. ?? ??? ??? ??? ??? ?printf("踩到雷,游戏结束\n");
  77. ?? ??? ??? ??? ??? ?show1(mine, row, col);
  78. ?? ??? ??? ??? ??? ?break;
  79. ?? ??? ??? ??? ?}
  80. ?? ??? ??? ?}
  81. ?? ??? ??? ?else
  82. ?? ??? ??? ?{
  83. ?? ??? ??? ??? ?printf("已经被排查\n");
  84. ?? ??? ??? ?}
  85. ?? ??? ?}
  86. ?? ??? ?else
  87. ?? ??? ?{
  88. ?? ??? ??? ?printf("坐标非法,请重新输入\n");
  89. ?? ??? ?}
  90. ?? ??? ?if (count == 0)
  91. ?? ??? ?{
  92. ?? ??? ??? ?printf("排雷成功");
  93. ?? ??? ??? ?show1(mine, row, col);
  94. ?? ??? ?}
  95. ?? ?}
  96. }
  97. int round_mineCount(char mine[][COLS],int x,int y)
  98. {
  99. ?? ?return ?( mine[x - 1][y] + mine[x + 1][y] +
  100. ?? ??? ?mine[x][y - 1] + mine[x][y + 1] +
  101. ?? ??? ?mine[x - 1][y - 1] + mine[x - 1][y + 1]
  102. ?? ??? ?+ mine[x + 1][y - 1] + mine[x + 1][y + 1]-8*'0');
  103. }

六、运行结果

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持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号