C語言實(shí)現(xiàn)簡(jiǎn)易版掃雷的完整過程
一、問題描述
用C語言實(shí)現(xiàn)簡(jiǎn)易版掃雷。
二、基本流程
1.菜單界面。
2.創(chuàng)建地圖 (兩個(gè)地圖)。
3.初始化地圖。
4.打印地圖。
5.程序讀取玩家輸入的要翻開位置的坐標(biāo),并校驗(yàn)。
6.如果不是地雷,統(tǒng)計(jì)當(dāng)前位置周圍雷的個(gè)數(shù), 并顯示到地圖上.。
7.判定游戲是否勝利。
三、步驟
1.菜單界面
1.開始游戲 0.退出游戲
int menu(){ printf("----------------------\n"); printf("------1.開始游戲------\n"); printf("------0.退出游戲------\n"); printf("----------------------\n"); int choice = 0; printf("請(qǐng)輸入你的選擇:"); scanf("%d", &choice); return choice; }
2.創(chuàng)建地圖
我們需要兩張地圖,所以要?jiǎng)?chuàng)建兩個(gè)二維數(shù)組。
第一個(gè)二維數(shù)組,表示玩家看到的地圖。(show)
第二個(gè)二維數(shù)組,表示當(dāng)前位置是不是地雷(1表示是地雷,0表示不是地雷)。(mine)
使用宏定義的原因:
1.推高代碼可讀性,后續(xù)代碼中遇到9,方便理解含義。
2.提高擴(kuò)展性,如果將來要修改棋盤尺寸,代碼修改會(huì)很方便。
#define MAX_ROW 9 #define MAX_COL 9 char show[MAX_ROW][MAX_COL] = { 0 }; char mine[MAX_ROW][MAX_COL] = { 0 };
3.初始化地圖
使用 * 表示未翻開的地。
show地圖一開始全都是 * 。
mine地圖是由0,1組成的。(1表示是地雷,0表示不是地雷)一開始都為0,隨后由電腦隨機(jī)在地圖上生成1。
這里我們使用宏定義了DIFFICULTY,表示地雷的數(shù)量:10個(gè)。
#define DIFFICULTY 10 void init(char show[MAX_ROW][MAX_COL], char mine[MAX_ROW][MAX_COL]){ for (int row = 0; row < MAX_ROW; row++){ for (int col = 0; col < MAX_COL; col++){ show[row][col] = '*'; //初始化 mine,先全設(shè)為'0', 然后隨機(jī)生成n個(gè)'1' mine[row][col] = '0'; } } int n = DIFFICULTY; while (n>0){ // 生成雷的隨機(jī)位置 int row = rand() % MAX_ROW; int col = rand() % MAX_COL; if (mine[row][col] == '1'){ // 如果當(dāng)前位置已經(jīng)有雷了,就直接進(jìn)入下次循環(huán), 重新產(chǎn)生隨機(jī)位置 continue; } mine[row][col] = '1'; n--; } }
4.打印地圖
打印出地圖。
void printMap(char themap[MAX_ROW][MAX_COL]){ printf(" |"); for (int col = 0; col < MAX_COL; col++) { printf("%d ", col); } printf("\n"); printf("--+------------------\n"); for (int row = 0; row < MAX_ROW; row++) { printf(" %d|", row); for (int col = 0; col < MAX_COL; col++) { printf("%c ", themap[row][col]); } printf("\n"); } }
5.玩家翻開坐標(biāo)
玩家通過輸入坐標(biāo)的方式翻開土地。
注意:
1.輸入坐標(biāo)要在地圖范圍內(nèi)。
2.不能重復(fù)翻開土地。
//程序讀取玩家輸入的要翻開位置的坐標(biāo), 并校驗(yàn) int row = 0; int col = 0; printf("請(qǐng)輸入翻開的坐標(biāo)(row col):"); scanf("%d %d", &row, &col); if (row < 0 || col < 0 || row >= MAX_ROW || col >= MAX_COL){ printf("輸入的坐標(biāo)超過范圍,重新輸入:\n"); continue; } if (show[row][col] != '*'){ printf("已經(jīng)翻開,請(qǐng)重新輸入:\n"); continue; }
6.判斷是否為地雷
如果翻開的位置在mine上顯示為1,那么翻到地雷了,輸出被炸死,打印地雷地圖,讓玩家死得明白。
如果翻開的位置上在mine上不是1,那么繼續(xù)下一步驟。
if (mine[row][col] == '1'){ printf("你已經(jīng)被炸死了?。?!\n"); printMap(mine); break; }
7.更新地圖
計(jì)算周圍的地雷數(shù)量,在翻開位置顯示。
updateShow(show,mine,row,col);
// 根據(jù)當(dāng)前 row, col 的位置, 計(jì)算出當(dāng)前位置周圍有幾個(gè)雷 // 并且更新顯示到 show 中 void updateShow(char show[MAX_ROW][MAX_COL], char mine[MAX_ROW][MAX_COL], int row, int col){ int count = 0; for (int r = row - 1; r <= row + 1; r++) { for (int c = col - 1; c <= col + 1; c++) { if (r < 0 || r >= MAX_ROW || c < 0 || c >= MAX_COL) { continue; } if (mine[r][c] == '1') { count++; } } } //此時(shí) count 里面就已經(jīng)存好了 row, col 周圍 八個(gè)格子 的雷的個(gè)數(shù) // 把這個(gè)結(jié)果寫到 show 中即可. // 需要把數(shù)字 count 轉(zhuǎn)成對(duì)應(yīng)的字符 show[row][col] = count + '0'; }
8.判斷是否勝利
定義一個(gè)變量safe,表示翻開的不是地雷的土地,每次更新地圖后,safe加一。如果最后翻開的不是地雷的土地等于地圖的大小減地雷數(shù),那么排除所有地雷,確認(rèn)安全。
//記錄翻開的格子的個(gè)數(shù) int safe = 0; updateShow(show,mine,row,col); safe++; if (safe == MAX_ROW*MAX_COL - DIFFICULTY){ printf("已經(jīng)排除所有的雷,你已經(jīng)安全?。?!\n"); printMap(mine); break; }
四、代碼實(shí)現(xiàn)
#define _CRT_SECURE_NO_WARNINGS #define MAX_ROW 9 #define MAX_COL 9 #define DIFFICULTY 10 #include <stdio.h> #include <time.h> #include <stdlib.h> int menu(){ printf("----------------------\n"); printf("------1.開始游戲------\n"); printf("------0.退出游戲------\n"); printf("----------------------\n"); int choice = 0; printf("請(qǐng)輸入你的選擇:"); scanf("%d", &choice); return choice; } void init(char show[MAX_ROW][MAX_COL], char mine[MAX_ROW][MAX_COL]){ for (int row = 0; row < MAX_ROW; row++){ for (int col = 0; col < MAX_COL; col++){ show[row][col] = '*'; mine[row][col] = '0'; } } int n = DIFFICULTY; while (n>0){ int row = rand() % MAX_ROW; int col = rand() % MAX_COL; if (mine[row][col] == '1'){ continue; } mine[row][col] = '1'; n--; } } void printMap(char themap[MAX_ROW][MAX_COL]){ printf(" |"); for (int col = 0; col < MAX_COL; col++) { printf("%d ", col); } printf("\n"); printf("--+------------------\n"); for (int row = 0; row < MAX_ROW; row++) { printf(" %d|", row); for (int col = 0; col < MAX_COL; col++) { printf("%c ", themap[row][col]); } printf("\n"); } } void updateShow(char show[MAX_ROW][MAX_COL], char mine[MAX_ROW][MAX_COL], int row, int col){ int count = 0; for (int r = row - 1; r <= row + 1; r++) { for (int c = col - 1; c <= col + 1; c++) { if (r < 0 || r >= MAX_ROW || c < 0 || c >= MAX_COL) { continue; } if (mine[r][c] == '1') { count++; } } } show[row][col] = count + '0'; } void game(){ char show[MAX_ROW][MAX_COL] = { 0 }; char mine[MAX_ROW][MAX_COL] = { 0 }; init(show, mine); int safe = 0; while (1){ printMap(show); int row = 0; int col = 0; printf("請(qǐng)輸入翻開的坐標(biāo)(row col):"); scanf("%d %d", &row, &col); if (row < 0 || col < 0 || row >= MAX_ROW || col >= MAX_COL){ printf("輸入的坐標(biāo)超過范圍,重新輸入:\n"); continue; } if (show[row][col] != '*'){ printf("已經(jīng)翻開,請(qǐng)重新輸入:\n"); continue; } if (mine[row][col] == '1'){ printf("你已經(jīng)被炸死了!?。n"); // 打印一遍地雷的地圖, 讓玩家死的明白 printMap(mine); break; } updateShow(show, mine, row, col); safe++; if (safe == MAX_ROW*MAX_COL - DIFFICULTY){ printf("已經(jīng)排除所有的雷,你已經(jīng)安全!??!\n"); // 打印一遍地雷的地圖, 讓玩家知道雷在哪 printMap(mine); break; } } } int main() { srand((unsigned int)time(0)); while (1){ int choice = menu(); if (choice == 1){ game(); } else if (choice == 0){ printf("退出游戲,byebye!"); break; } else{ printf("輸入錯(cuò)誤,請(qǐng)重新輸入:"); continue; } } }
總結(jié)
到此這篇關(guān)于C語言實(shí)現(xiàn)簡(jiǎn)易版掃雷的文章就介紹到這了,更多相關(guān)C語言簡(jiǎn)易版掃雷內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
在QT5中實(shí)現(xiàn)求兩個(gè)輸入值的和并輸出(實(shí)例)
下面小編就為大家?guī)硪黄赒T5中實(shí)現(xiàn)求兩個(gè)輸入值的和并輸出(實(shí)例)。小編覺得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧2017-08-08C語言自定義類型超詳細(xì)梳理之結(jié)構(gòu)體 枚舉 聯(lián)合體
今天我們來學(xué)習(xí)一下自定義類型,自定義類型包括結(jié)構(gòu)體、枚舉、聯(lián)合體,小編覺得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考2022-03-03C++ clock()解析如何使用時(shí)鐘計(jì)時(shí)的應(yīng)用
本篇文章是對(duì)c++中的clock()函數(shù)進(jìn)行了詳細(xì)的分析介紹,需要的朋友參考下2013-06-06C++?OpenCV實(shí)現(xiàn)boxfilter方框?yàn)V波的方法詳解
box?filter的作用很簡(jiǎn)單,即對(duì)局部區(qū)域求平均,并把值賦給某個(gè)點(diǎn),一般我們賦給區(qū)域中心。本文將用C++實(shí)現(xiàn)boxfilter方框?yàn)V波,需要的可以了解一下2022-10-10C++ 實(shí)現(xiàn)即時(shí)通信的示例代碼(直接運(yùn)行)
本文主要介紹了C++ 實(shí)現(xiàn)即時(shí)通信的示例代碼,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2022-05-05