LeetCode 542

传送门:https://leetcode-cn.com/problems/01-matrix/

给定一个由 0 和 1 组成的矩阵,找出每个元素到最近的 0 的距离。

两个相邻元素间的距离为 1 。

示例 1:
输入:

0 0 0
0 1 0
0 0 0
输出:

0 0 0
0 1 0
0 0 0
示例 2:
输入:

0 0 0
0 1 0
1 1 1
输出:

0 0 0
0 1 0
1 2 1
注意:

给定矩阵的元素个数不超过 10000。
给定矩阵中至少有一个元素是 0。
矩阵中的元素只在四个方向上相邻: 上、下、左、右。

这个题我一开始也是想用泛洪法去检测,当遇到1的时候就开始向四周看到达0的最短距离,但是我发现这样做实现不了,而且扫描浪费时间也很大。遂去看解析。

https://leetcode-cn.com/problems/01-matrix/solution/2chong-bfs-xiang-jie-dp-bi-xu-miao-dong-by-sweetie/

看了这个解析的BFS解法,我有点明白了。下面讲讲我个人理解的思路。

新建一个queue用于保存已经扫描过节点的XY坐标,新建一个visited数组用于判别当前的位置是否已经访问过,result数组用于保存结果。

第一轮先对整个传入的数组进行遍历,扫描到0的直接入队、保存到visited数组并且将对应的result位置设置为0

因为当前位置为0的不需要去看其他节点是否为0,它本身就是可以满足条件的。

当第一轮做完以后,我们再取队列中的元素,分别让他上下左右移动。

 if(newX>=0 && newY>=0 && newX < matrix.length && newY< matrix[0].length && !visit[newX][newY])

这行代码用于判断是否越界或者是已经访问过,如果是就直接跳到下一次移动操作。

visit[newX][newY] = true;
                    res[newX][newY] = res[x][y] + 1;
                    queue.add(new Integer[]{newX,newY});

因为matrix中所有为1的节点都是没有访问过的,所以先将visited数组置为true以表示这次访问到了。

然后将其值直接改为res[x][y](当前节点为0)+1(从0开始1步就可以访问到这个1节点)。

然后将最新的节点添加到队列中,以防止出现 [1,1,1]这种多个1包含在一起的情况。

总体代码:

 1 class Solution {
 2     public int[][] updateMatrix(int[][] matrix) {
 3         if(matrix == null || matrix.length == 0){
 4             return null;
 5         }
 6         int[][] direction = new int[][] {{-1,0},{1,0},{0,-1},{0,1}};
 7         Queue<Integer[]>queue = new LinkedList<>();
 8         int m = matrix.length, n = matrix[0].length;
 9         boolean[][] visit = new boolean[m][n];
10         int[][] res = new int[m][n];
11         for(int i = 0; i < m;i++){
12             for(int j = 0; j < n;j++){
13                 if(matrix[i][j] == 0){
14                     queue.add(new Integer[]{i,j});
15                     visit[i][j] = true;
16                     res[i][j] =0;
17                 }
18             }
19         }
20 
21         while(!queue.isEmpty()){
22             Integer[] temp = queue.poll();
23             int x = temp[0];
24             int y = temp[1];
25             for(int i = 0; i < direction.length;i++){
26                 int newX = x + direction[i][0];
27                 int newY = y+ direction[i][1];
28                 if(newX>=0 && newY>=0 && newX < matrix.length && newY< matrix[0].length && !visit[newX][newY]){
29                     visit[newX][newY] = true;
30                     res[newX][newY] = res[x][y] + 1;
31                     queue.add(new Integer[]{newX,newY});
32                 }
33             }
34         }
35         return res;
36     }
37 }
View Code
原文地址:https://www.cnblogs.com/ZJPaang/p/12706229.html