• 01矩阵


    问题描述

    给定矩阵,求出每个元素离最近的 0 的距离,注意最近的 0 可以不和该元素同一行

    输入案例

    0 0 0
    0 1 0
    1 1 1

    输出

    0 0 0
    0 1 0
    1 2 1

    解决思路

      咋一看貌似可以用DP来做哎,如果知道了一个元素的附近邻居的最小距离,然后取邻居的最小距离+1不就出来了嘛。大体思路确实如此,但是怎样获得邻居元素的结果呢?

    具体思路

      我们在遍历的时候总是根据从左到右、从上到下的顺序来的,对于某个我们想要考虑的元素,如果他的左边邻居和上面的邻居都已经被计算过,那么我们就可以根据他的左、上边邻居得到他的计算结果值。第一次遍历结束后,还只是考虑了从左上邻居的情况,没有考虑右下邻居的情况,然后再进行一次遍历,从右往左、从下往上遍历,此时就可以根据右、下邻居计算出一个值,这个值要和第一遍根据左上邻居计算出来的结果进行比较取小。即得到该位置处的计算结果。

      可能有同学会问了,为什么不能用一次遍历呢,直接把该元素的上下左右四个邻居全部考虑进来呢?对于这个问题,我肯定是摔过跟头的啊!我们可以考虑这样一点,从上到下,从左到右遍历的时候,对于给定位置的元素,他的左上邻居才有计算结果,右下邻居根本还没得到计算,怎么可以把非计算结果代带进去比较呢?举个例子,比如矩阵中的某个小区域是这个样子:

    1 0 1 1
    1 1 1 1
    0 0 1 1
    1 0 1 1

    只遍历一次的前两行结果为:
    1 0 1 2
    1 1 2 2

      对于第2行最后一个结果,明显错了对不对,因为他直接把他的下邻居的 1 拿来计算了。

    Java 实现

     1 class Solution {
     2     private static int[] dx = {-1, 0, 1, 0}; //  上 左 下 右
     3     private static int[] dy = {0, -1, 0, 1};
     4     
     5     public static int[][] updateMatrix(int[][] matrix) {
     6         int m = matrix.length, n = matrix[0].length;
     7         for (int i = 0; i < m; i++) {
     8             for (int j = 0; j < n; j++) {
     9                 if (matrix[i][j] == 0) continue;
    10                 int newI, newJ, min=10001;
    11                 // 左、上邻居
    12                 for (int k = 0; k < 2; k++) {
    13                     newI = i + dx[k];
    14                     newJ = j + dy[k];
    15                     if (0 <= newI && newI < m && 0 <= newJ && newJ < n) {
    16                         min = Math.min(min, matrix[newI][newJ]);
    17                     }
    18                 }
    19                 matrix[i][j] = min + 1;
    20             }
    21         }
    22         for (int i = m-1; i >=0; i--) {
    23             for (int j = n-1; j >=0; j--) {
    24                 if (matrix[i][j] == 0) continue;
    25                 int newI, newJ, min=10001;
    26                 // 右 下邻居
    27                 for (int k = 2; k < 4; k++) {
    28                     newI = i + dx[k];
    29                     newJ = j + dy[k];
    30                     if (0 <= newI && newI < m && 0 <= newJ && newJ < n) {
    31                         min = Math.min(min, matrix[newI][newJ]);
    32                     }
    33                 }
    34                 matrix[i][j] = Math.min(matrix[i][j], min + 1);
    35             }
    36         }
    37         return matrix;
    38     }
    39 }        
  • 相关阅读:
    服务部署 RPC vs RESTful
    模拟浏览器之从 Selenium 到splinter
    windows程序设计 vs2012 新建win32项目
    ubuntu python 安装numpy,scipy.pandas.....
    vmvare 将主机的文件复制到虚拟机系统中 安装WMware tools
    ubuntu 修改root密码
    python 定义类 简单使用
    python 定义函数 两个文件调用函数
    python 定义函数 调用函数
    python windows 安装gensim
  • 原文地址:https://www.cnblogs.com/dogeLife/p/11378456.html
Copyright © 2020-2023  润新知