305. Number of Islands II


本来懒得记录= =但是找工作前的代码真是丢人。。。

这应该是UF最好的应用之一了。

  • 二维转一维建UF
  • 需要注意 x * col + y
  • 算完结果的i再传到union或者find里比find(x, y)这样进去再算好多了。。我是不是傻逼啊
  • UNION的标准是题的关键,
  • 上下左右相邻。不用UF做的话牵扯一个问题,比如上面下面是一个岛,有可能会算2次,UF没这个问题了= =
  • UNION了相应岛的数量-1,所以UF里可以自定义一些东西来实时更新,比如当前岛的数量,上一题是最大岛的面积

最难的是二维转一维,好久没做了。然后一开始犹豫了初始化,是不是要全部PARENT[]都设0,答案是没必要……
然后树随意压缩下。。懒得全指ROOT了。。重点不是这个
时间复杂度要求k*log(mn) k是add岛屿的数量 logMN就是UF里树的高度= =感觉这是赤裸裸的提示,知道时间复杂度基本就知道UF了。。

这里其实有BUG的integer的比较用==如果-127~128范围之外会错误,还是得.equals. 然后UNION的时候忘更新WEIGHT了。。。。

class Solution {
    
    public class WeightedUF {
        int num;
        Map<Integer, Integer> parents;
        Map<Integer, Integer> size;
        
        public WeightedUF() {
            num = 0;
            parents = new HashMap<>();
            size = new HashMap<>();
        }
        
        public Integer find(Integer n) {
            if (n == null || !parents.containsKey(n)) return null;
            Integer root = n;
            while (root != parents.get(root)) {
                parents.put(root, parents.get(parents.get(root)));
                root = parents.get(root);
            }
            return root;
        }
        
        public void union(Integer a, Integer b) {
            Integer rootA = find(a);
            Integer rootB = find(b);
            if (rootA == null || rootB == null || rootA == rootB) return;
            
            Integer sizeA = size.get(a);
            Integer sizeB = size.get(b);
            parents.put(sizeA > sizeB ? rootB : rootA, sizeA > sizeB ? rootA : rootB);
            num --;
            return;
        }
        
        public void add(Integer n) {
            if (!parents.containsKey(n)) {
                parents.put(n, n);
                size.put(n, 1);
                num ++;
            }
        }
    }
    
    public List<Integer> numIslands2(int m, int n, int[][] positions) {
        List<Integer> result = new ArrayList<>();
        if (positions.length == 0 || positions[0].length == 0) return result;
        
        WeightedUF uf = new WeightedUF();
        
        for (int[] pair : positions) {
            int x = pair[0];
            int y = pair[1];
            Integer i = x * n + y;
            uf.add(i);
            
            // right
            if (x + 1 < m) uf.union(i, (x + 1) * n + y);
            // left
            if (x - 1 >= 0) uf.union(i, (x - 1) * n + y);
            // up
            if (y + 1 < n) uf.union(i, (x * n + y + 1));
            // down
            if (y - 1 >= 0) uf.union(i, (x * n + y - 1));
            
            result.add(uf.num);
        }
        
        return result;
    }
}
posted @ 2017-01-14 06:47  哇呀呀..生气啦~  阅读(187)  评论(0)    收藏  举报