版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/qq_37867156/article/details/82695636
描述
给定一个N行M列的01矩阵 A,A[i][j] 与 A[k][l] 之间的曼哈顿距离定义为:
dist(A[i][j],A[k][l])=|i-k|+|j-l|
输出一个N行M列的整数矩阵B,其中:
B[i][j]=min(1≤x≤N,1≤y≤M,A[x][y]=1){dist(A[i][j],A[x][y])}
即求与每个位置曼哈顿距离最近的1
N,M≤1000。
输入格式
第一行两个整数n,m。
接下来一个N行M列的01矩阵,数字之间没有空格。
输出格式
一个N行M列的矩阵B,相邻两个整数之间用一个空格隔开。
样例输入
3 4 0001 0011 0110
样例输出
3 2 1 0 2 1 0 0 1 0 0 1
题解:P108。将矩阵 A 中每一个 1 都看作起点,整个矩阵的所有位置都可以通行,对于每个位置,在从任何一个起点出发都可以的情况下,求到达该位置所需的最少步数。
扫描二维码关注公众号,回复:
3400185 查看本文章
#include <iostream>
#include <algorithm>
#include <cstdio>
#include <cstring>
#include <queue>
#define ll long long
using namespace std;
const int maxn = 1000+7;
int n, m;
char a[maxn][maxn];
int b[maxn][maxn];
const int dx[4] = {-1,1,0,0}, dy[4] = {0,0,-1,1};
queue<pair<int, int> > q;
int main()
{
cin >> n >> m;
for(int i = 1; i <= n; i++)
scanf("%s", a[i] + 1);
memset(b, -1, sizeof b);
for(int i = 1; i <= n; i++) {
for(int j = 1; j <= m; j++) {
if(a[i][j] == '1')
q.push(make_pair(i, j)), b[i][j] = 0;
}
}
while(q.size()) {
pair<int, int> now = q.front();
q.pop();
for(int i = 0; i < 4; i++) {
pair<int, int> next(now.first+dx[i], now.second+dy[i]);
if(next.first < 1 || next.second < 1 || next.first > n || next.second > m)
continue;
if(b[next.first][next.second] == -1){
b[next.first][next.second] = b[now.first][now.second] + 1;
q.push(next);
}
}
}
for(int i = 1; i <= n; i++) {
for(int j = 1; j <= m; j++)
printf("%d ", b[i][j]);
puts("");
}
return 0;
}