用数组表示一个10x9的二维格子,其中数字9表示雷,0表示非雷,请在非雷单元格里标注周围的雷的数目,初始格子都是隐藏的,请根据输入的格子坐标按下面的要求将格子打开: 1、如果这个格子是雷,请将所有的雷标出。 2、如果这个格子是1-8的数字,请只打开这个格子。 3、如果这个格子是0,请将周围8邻域所有是0的格子都打开,直到格子里的值是1-8的数字(包含数字的格子也打开)。 输入10x9个数字,其中数字9表示雷,0表示非雷,两个表示坐标的数字,坐标从0开始。输出一行10个字符,字符间用一个空格隔开,其中@表示格子隐藏,打开的格子*表示雷,1-8表示周围的雷数,0个雷输出空格。 。使用c++
时间: 2023-10-02 19:11:03 浏览: 46
以下是我编写的程序,可以实现你所需的功能:
```c++
#include <iostream>
#include <vector>
using namespace std;
const int ROW = 10; // 行数
const int COL = 9; // 列数
// 判断坐标是否在格子内
bool inGrid(int x, int y) {
return x >= 0 && x < ROW && y >= 0 && y < COL;
}
int main() {
// 读入雷区
int grid[ROW][COL];
for (int i = 0; i < ROW; i++) {
for (int j = 0; j < COL; j++) {
cin >> grid[i][j];
}
}
// 标记雷数
vector<vector<int>> nums(ROW, vector<int>(COL)); // 存储每个格子周围的雷数
for (int i = 0; i < ROW; i++) {
for (int j = 0; j < COL; j++) {
if (grid[i][j] == 9) {
nums[i][j] = -1; // 雷的标记为-1
continue;
}
int count = 0;
for (int x = i - 1; x <= i + 1; x++) {
for (int y = j - 1; y <= j + 1; y++) {
if (inGrid(x, y) && grid[x][y] == 9) {
count++;
}
}
}
nums[i][j] = count;
}
}
// 处理输入的坐标
int x, y;
cin >> x >> y;
int value = grid[x][y];
if (value == 9) { // 点到雷了
for (int i = 0; i < ROW; i++) {
for (int j = 0; j < COL; j++) {
if (grid[i][j] == 9) {
cout << "* ";
} else {
cout << nums[i][j] << " ";
}
}
cout << endl;
}
} else if (value >= 1 && value <= 8) { // 点到数字了
grid[x][y] = -1; // 标记为已打开
nums[x][y] = value;
for (int i = 0; i < ROW; i++) {
for (int j = 0; j < COL; j++) {
if (grid[i][j] == 9) {
cout << "@ ";
} else if (grid[i][j] == -1) {
cout << nums[i][j] << " ";
} else {
cout << "@ ";
}
}
cout << endl;
}
} else { // 点到空格
grid[x][y] = -1; // 标记为已打开
vector<vector<bool>> visited(ROW, vector<bool>(COL)); // 标记是否已访问
visited[x][y] = true;
for (int i = 0; i < ROW; i++) {
for (int j = 0; j < COL; j++) {
if (grid[i][j] == 9) {
cout << "@ ";
} else if (grid[i][j] == -1 || (!visited[i][j] && nums[i][j] > 0)) {
cout << nums[i][j] << " ";
} else {
// 广度优先搜索
vector<pair<int, int>> queue;
queue.push_back(make_pair(i, j));
while (!queue.empty()) {
int x = queue.back().first;
int y = queue.back().second;
queue.pop_back();
visited[x][y] = true;
grid[x][y] = -1;
if (nums[x][y] == 0) { // 如果周围没有雷,继续搜索
for (int dx = -1; dx <= 1; dx++) {
for (int dy = -1; dy <= 1; dy++) {
int nx = x + dx;
int ny = y + dy;
if (inGrid(nx, ny) && !visited[nx][ny]) {
queue.push_back(make_pair(nx, ny));
}
}
}
}
}
cout << "@ ";
}
}
cout << endl;
}
}
return 0;
}
```
程序的大致思路如下:
1. 读入雷区,并标记每个格子周围的雷数。
2. 处理用户输入的坐标。
3. 如果坐标点到了雷,将所有的雷标出。
4. 如果坐标点到了数字,只打开这个格子。
5. 如果坐标点到了空格,将周围所有是0的格子都打开,直到格子里的值是1-8的数字。
程序中用了一个 vector<vector<int>> 存储每个格子周围的雷数,用一个 vector<vector<bool>> 标记是否已访问。在处理空格时,使用广度优先搜索算法来搜索周围的格子。