【C语言】扫雷(包括展开和标记)(一)

简介: 【C语言】扫雷(包括展开和标记)

前言

🎈大家好,我是何小侠🎈

🌀大家可以叫我**小何或者小侠🌀**

🔴我是一名普通的博客写作者🔴

💐希望能通过写博客加深自己对于学习内容的理解💐

🌸也能帮助更多人理解和学习🌸

🍃我的主页:何小侠的主页🍃



    这篇博客我们一起来学习如何用C语言所学知识来实现扫雷,另外我们还将学习一个难点TNT式展开。希望能帮助大家理解和学习

    🍊

    引子🍊

    扫雷最原始的版本可以追溯到1973年一款名为“方块”的游戏。
    不久,“方块”被改写成了游戏“Rlogic”。在“Rlogic”里,玩家的任务是作为美国海军陆战队队员,为指挥中心探出一条没有地雷的安全路线,如果路全被地雷堵死就算输。两年后,汤姆·安德森在“Rlogic”的基础上又编写出了游戏“地雷”,由此奠定了现代扫雷游戏的雏形。

    1981年, 微软公司的 罗伯特·杜尔 和 卡特·约翰逊 两位工程师在Windows

    3.1系统上加载了该游戏,扫雷游戏才正式在全世界推广开来。 扫雷很快在全球范围内流行开来,成为Windows操作系统中最受欢迎的游戏之一。许多人在办公室和家庭中都玩这个游戏来消磨时间。**

    随着移动设备的普及,扫雷也进入了移动设备领域。现在,扫雷已经成为了一种经典的游戏,被广泛地应用于各种平台和设备中。

    游戏思路🍊

    我们看一下我们的扫雷游戏的图片

    这就是我们熟悉的扫雷游戏,虽然我们现在没有能力将它100%的复刻出来,但是大部分的逻辑在我们的努力下是能够做到的。

    首先我们看一下简单的逻辑

    我们点击这个数字为2的方格后,这个方格显示了2的数字,这就是告诉我们在这个九宫格内,一共有两个雷。

    我点击随机点击这个九宫格,直达有雷,最后我们看到确实是这样。(当然我们后面也会介绍TNT式展开)

    现在我们应该就能大致理解这个游戏了,大概的思路是:

    • 首先要有雷。
    • 然后再排雷。
    • 如果排到了雷就游戏结束,如果没有排到,就应该显示一下周围有几个雷,然后继续排。
    • 游戏胜利——我们将所有的雷找出来,或者拍完所有非雷坐标。

    但是我们肯定需要东西来存储扫雷的数据,用什么呢?

    对, 应该是数组而且是二维数组,由于我们后面主要将9x9,所以我们就需要一个9x9的二维数组,但是这其中还是有一点细节的。下面我们将会探讨。

    我们在给二维数组初始化的时候,如果用‘1’表示雷,‘0’表示非雷。

    由于‘0’太多了我就不画完了。

    我们会发现一个问题如果在九宫格里只有一个雷的时候,我们这个‘1’就存在歧义了,

    但是有人想说,那我就不用‘1’‘0’表示雷和非雷不就行了吗?我用‘’和‘#’表示雷与非雷就行
    但是如果这样我们的数组的内容就很杂乱,我们和我们玩的扫雷就存在很大的差距,我们在电脑上玩的扫雷游戏总体上只有三种内容,要么是空格,要么是数字,要么是雷。那我们应该怎么办呢?

    我们就可以用两个大小相同的二维数组,一个专门放置雷,一个就专门用来展示有关于雷的信息,这个信息也是从放置雷的数组得来的。

    下面给出参考
    我们在放置雷的数组中只用‘1’,‘0’。在展示给玩家的数组中,没有被排查的位置全部置为‘
    ’保持神秘感,然后排查的位置就用与九宫格雷数相等的字符数字来表示

    所以我们定义两个数组 char mine[ 9 ][ 9 ], char show[ 9 ][ 9 ]

    但是我们现在任然存在一个问题。

    我们在mine数组检测玩家点击的方格时,如果玩家点击到的是最外层的方格,我们就会越界访问。

    怎么解决呢?

    那我们就直接把数字开大一点就行char mine[ 11 ][ 11 ],我特意画了一个图来展示。

    可以看到即使我们在9x9棋盘的边缘查找,也不会越界。为了保证mine数组和show数组是严格对应的,我们也把show数组开大一点,变成show[ 11 ][ 11 ]。

    这就是我们大概的游戏思路,接下来我们开始实现。

    定义和初始化

    void game()
    {
      //定义二维数组
      char mine[ROWS][COLS];
      char show[ROWS][COLS];
      ······
      }

    我们暂时先给出一点代码,避免干扰思路,

    注意看我们用的常量ROWS,和COLS来定义。

    这是我们在头文件用#define定义的,为什么我们还非要写ROW,和COL呢?因为我们有时候不需要操作整个数组,只需要操作9x9就行。

    然后是我们的初始化->

    void game()
    {
      //定义二维数组
      char mine[ROWS][COLS];
      char show[ROWS][COLS];
      //初始化二维数组
      init_arr(mine, ROWS, COLS, '0');
      init_arr(show, ROWS, COLS, '*');
          ·······
    //初始化二维数组
    void init_arr(char arr[ROWS][COLS], int rows, int cols, char ch)
    {
      int i = 0;
      int j = 0;
      for (i = 0; i < rows; i++)
      {
        for (j = 0; j < cols; j++)
        {
           arr[i][j] = ch;
        }
      }
    }

    可以看到我们传的最后一个参数,我们可以根据你要初始化什么字符来使用这个函数,也是这个初始化比较好的部分。

    这个还有一个要注意的地方,我们写形参的时候不能写char arr[ROW][COL],因为我们传的是整个数组。我们后来用小写 rows,cols表示ROWS,COLS增加可读性,避免一直用大写ROWS,COLS,当然用也没什么问题,但是我感觉小写看着舒服一点。

    打印棋盘

    打印棋盘没有太多要讲的,格式大家可以多调一调。

    void game()
    {
      //定义二维数组
      char mine[ROWS][COLS];
      char show[ROWS][COLS];
      //初始化二维数组
      init_arr(mine, ROWS, COLS, '0');
      init_arr(show, ROWS, COLS, '*');
      //打印二维数组
      display (show, ROW, COL);
      ··········
    void display(char arr[ROWS][COLS], int row, int col)
    {
      printf("·················扫雷·················\n");
      int i = 0;
      int j = 0;
      for (i = 0; i <= row; i++)
      {
        printf(" %d ", i);
        if (i > 0)
        printf(" ");
      }
      printf("\n");
      printf("\n");
      for (i = 1; i <= row; i++)
      {
        printf(" %d ", i);
        for (j = 1; j <= col; j++)
        {
          printf(" %c ", arr[i][j]);
          if (j <= col -1)
          printf("|");
        }
        printf("\n");
        if (i <= row - 1)
        {
          printf("   ");
          for (j = 0; j < col; j++)
          {
            printf("---");
            if (j < col - 1)
              printf("|");
          }
          printf("\n");
        }
      }
        printf("·················扫雷··················\n");
    }

    有过要注意的点,我们打印的数组下标是从1开始,因为最外围是我们不需要用的,我上面有一张图可以看,这里就不再插入图片了。

    如果有人看不太懂可以去看看我三子棋的博客>:链接: link

    打印出来效果就是这样。我感觉看起来比起一堆数字还是舒服一点。但是这个提示的几行几列数字不是很好打印,要多调整调整。当然我们也可以打印show数组,打印出来就全是‘*’

    布置雷

    我们想要布置雷,那我们一定是要在mine数组,我们只需要在9x9的领域布置,那我们就只需要传ROW,COL。我们也还有设定一下雷的数量,埋完就不埋了。

    void game()
    {
      //定义二维数组
      char mine[ROWS][COLS];
      char show[ROWS][COLS];
      //初始化二维数组
      init_arr(mine, ROWS, COLS, '0');
      init_arr(show, ROWS, COLS, '*');
      //打印二维数组
      display (show, ROW, COL);
      //埋雷
      set_mine (mine, ROW, COL);
      ······
      }
    void set_mine(char mine[ROWS][COLS], int row, int col)
    {
      int x = 0;
      int y = 0;
      int count = EASY;
      while (count)
      {
        x = rand() % row + 1;
        y = rand() % col + 1;
        if (x > 0 && x <= row && y > 0 && y <= col && mine[x][y]!='1')
        {
          mine[x][y] = '1';
          count--;
        }
      }
    }

    如果有小伙伴看不懂rand()这个函数的用法可以看看我的这篇博客.

    链接: link

    这里我就直接用EASY表示简单模式了,只埋10个雷。


    目录
    相关文章
    |
    29天前
    |
    C语言
    扫雷游戏(用C语言实现)
    扫雷游戏(用C语言实现)
    73 0
    |
    3月前
    |
    机器学习/深度学习 C语言
    九/十:《初学C语言》— 扫雷游戏实现和函数递归基础
    【8月更文挑战第5天】本篇文章用C语言采用多文件编写实现了一个基础的扫雷游戏(附源码),并讲解了关于函数递归的基础概念及其相对应的习题练习(附源码)
    40 1
    九/十:《初学C语言》— 扫雷游戏实现和函数递归基础
    |
    2月前
    |
    存储 安全 算法
    C 语言——实现扫雷小游戏
    本文介绍了使用二维数组创建棋盘并实现扫雷游戏的方法。首先,通过初始化数组创建一个9x9的棋盘,并添加行列标识以便操作。接着,利用随机数在棋盘上布置雷。最后,通过判断玩家输入的坐标来实现扫雷功能,包括显示雷的数量和处理游戏胜利或失败的情况。文中提供了完整的代码实现。
    42 1
    C 语言——实现扫雷小游戏
    |
    1月前
    |
    存储 算法 安全
    C语言实现扫雷游戏
    C语言实现扫雷游戏
    |
    30天前
    |
    C语言
    初学者指南:使用C语言实现简易版扫雷游戏
    初学者指南:使用C语言实现简易版扫雷游戏
    31 0
    |
    1月前
    |
    C语言
    C语言扫雷游戏(详解)
    C语言扫雷游戏(详解)
    36 0
    |
    1月前
    |
    存储 编译器 C语言
    【C语言篇】数组和函数的实践:扫雷游戏(附源码)
    【C语言篇】数组和函数的实践:扫雷游戏(附源码)
    34 0
    |
    3月前
    |
    C语言
    扫雷(C语言)
    扫雷(C语言)
    43 4
    |
    4月前
    |
    存储 编译器 C语言
    |
    5月前
    |
    C语言
    【海贼王编程冒险 - C语言海上篇】怎样用C语言实现简单的扫雷游戏?
    【海贼王编程冒险 - C语言海上篇】怎样用C语言实现简单的扫雷游戏?
    30 1