枚举每个非雷格的八个方向邻格,统计周围地雷数量并生成答案矩阵。
OJ: luogu
题目 ID: P2670
难度:入门
标签:模拟矩阵枚举python
日期: 2026-07-15 21:22
题意
给出扫雷棋盘,* 表示地雷,? 表示非雷格。对每个非雷格,输出它周围八个方向中地雷的个数;地雷格仍输出 *。
思路
先列出八个方向:
python
(-1,-1), (-1,0), ..., (1,1)枚举每个格子:
- 如果当前是
*,答案也是*; - 否则枚举八个邻格,检查是否在边界内且为
*,统计数量。
每一行用字符列表构造,最后 "".join(current) 变成输出字符串。
Python 知识
/home/rainboy/mycode/hugo-blog/content/program_language/python/input_output_and_strings.md:字符网格可按行保存为字符串列表。/home/rainboy/mycode/hugo-blog/content/program_language/python/brute_force_validation.md:二维矩阵枚举常用for row/for col双循环。0 <= nr < n and 0 <= nc < m是常见边界判断。"\n".join(answer)一次输出多行。
代码
python
directions = [
(-1, -1), (-1, 0), (-1, 1),
(0, -1), (0, 1),
(1, -1), (1, 0), (1, 1),
]
n, m = map(int, input().split())
grid = [input().strip() for _ in range(n)]
answer = []
for row in range(n):
current = []
for col in range(m):
if grid[row][col] == "*":
current.append("*")
continue
count = 0
for dr, dc in directions:
nr = row + dr
nc = col + dc
if 0 <= nr < n and 0 <= nc < m and grid[nr][nc] == "*":
count += 1
current.append(str(count))
answer.append("".join(current))
print("\n".join(answer))cpp
/**
* Author by Rainboy blog: https://rainboylv.com github: https://github.com/rainboylvx
* rbook: -> https://rbook.roj.ac.cn https://rbook2.roj.ac.cn
* rainboy的学习导航网站: https://idx.roj.ac.cn
* create_at: 2026-07-27 00:00
* update_at: 2026-07-27 00:00
*/
#include <bits/stdc++.h>
using namespace std;
const int MAXN = 105;
int n, m;
char grid[MAXN][MAXN]; // 地图,'*' 表示地雷
// 8 个方向:上左、上、上右、左、右、下左、下、下右
int dr[8] = {-1, -1, -1, 0, 0, 1, 1, 1};
int dc[8] = {-1, 0, 1, -1, 1, -1, 0, 1};
// 统计 (r,c) 周围 8 格的地雷数量
int count_mine(int r, int c) {
int cnt = 0;
for (int d = 0; d < 8; d++) {
int nr = r + dr[d];
int nc = c + dc[d];
if (nr >= 0 && nr < n && nc >= 0 && nc < m && grid[nr][nc] == '*')
cnt++;
}
return cnt;
}
int main() {
ios::sync_with_stdio(false);
cin.tie(nullptr);
cin >> n >> m;
for (int i = 0; i < n; i++) {
cin >> grid[i];
}
for (int i = 0; i < n; i++) {
for (int j = 0; j < m; j++) {
if (grid[i][j] == '*')
cout << '*';
else
cout << count_mine(i, j);
}
cout << "\n";
}
return 0;
}复杂度
每个格子最多检查 8 个方向,时间复杂度是
总结
网格邻域题先固定方向数组,再对每个格子套同一套边界判断和统计逻辑。