542. 01 矩阵
542. 01 矩阵
给定一个由 0 和 1 组成的矩阵,找出每个元素到最近的 0 的距离。
两个相邻元素间的距离为 1 。
示例:
输入:
0 0 0
0 1 0
1 1 1
0 1 0
1 1 1
输出:
0 0 0
0 1 0
1 2 1
0 1 0
1 2 1
注意:
给定矩阵的元素个数不超过 10000。
给定矩阵中至少有一个元素是 0。
矩阵中的元素只在四个方向上相邻: 上、下、左、右。
思路:
假设这个矩阵中恰好只有一个 0,那么对于每一个 1,离它最近的 0 就是那个唯一的 0。
我们可以从 0 的位置开始进行 广度优先搜索。广度优先搜索可以找到从起点到其余所有点的 最短距离,因此如果我们从 0 开始搜索,每次搜索到一个 1,就可以得到 0 到这个 1 的最短距离,也就离这个 1 最近的 0 的距离了(因为矩阵中只有一个 0)。
在广度优先搜索的每一步中,如果我们从矩阵中的位置 x 搜索到了位置 y,并且 y 还没有被搜索过,那么位置 y 离 0 的距离就等于位置 x 离 0 的距离加上 1。
我们在进行广度优先搜索的时候会使用到队列,在只有一个 0 的时候,我们在搜索前会把这个 0 的位置加入队列,才能开始进行搜索;如果有多个 0,我们只需要把这些 0 的位置都加入队列就行了。
在实际的题目中,我们会有不止一个 0。我们会想,要是我们可以把这些 0 看成一个整体好了。有了这样的想法,我们可以添加一个「超级零」,它与矩阵中所有的 0 相连,这样的话,任意一个 1 到它最近的 0 的距离,会等于这个 1 到「超级零」的距离减去一。由于我们只有一个「超级零」,我们就以它为起点进行广度优先搜索。这个「超级零」只和矩阵中的 0 相连,所以在广度优先搜索的第一步中,「超级零」会被弹出队列,而所有的 0 会被加入队列,它们到「超级零」的距离为 1。这就等价于:一开始我们就将所有的 0 加入队列,它们的初始距离为 0。这样以来,在广度优先搜索的过程中,我们每遇到一个 1,就得到了它到「超级零」的距离减去一,也就是 这个 1 到最近的 0 的距离。
代码:
class Solution { struct Node { int x, y; }node; public: vector<vector<int>> updateMatrix(vector<vector<int>>& matrix) { int m = matrix.size(); int n = matrix[0].size(); vector<vector<int>> visited(m, vector<int>(n,0)); vector<vector<int>> dist(m, vector<int>(n,0)); int i, j; queue<Node> Q; Node temp; int X[4] = {0, 0, 1, -1}; int Y[4] = {1, -1, 0, 0}; for(i = 0; i < m; i++) { for(j = 0; j < n; j++) { if(matrix[i][j] == 0) { node.x = i; node.y = j; Q.push(node); visited[i][j] = 1; } } } while(!Q.empty()) { node = Q.front(); Q.pop(); for(i = 0; i<4; i++) { temp.x = node.x + X[i]; temp.y = node.y + Y[i]; if(temp.x>=0&&temp.x<m&&temp.y>=0&&temp.y<n&&!visited[temp.x][temp.y]) { visited[temp.x][temp.y] = 1; dist[temp.x][temp.y] = dist[node.x][node.y]+1; Q.push(temp); } } } return dist; } };
posted on 2020-08-04 00:39 Little-Prince 阅读(165) 评论(0) 收藏 举报
浙公网安备 33010602011771号