LeetCode 286 - Walls and Gates


[LeetCode] Walls and Gates - jcliBlogger - 博客园
You are given a m x n 2D grid initialized with these three possible values.
  1. -1 - A wall or an obstacle.
  2. 0 - A gate.
  3. INF - Infinity means an empty room. We use the value 231 - 1 = 2147483647 to represent INF as you may assume that the distance to a gate is less than2147483647.
Fill each empty room with the distance to its nearest gate. If it is impossible to reach a gate, it should be filled with INF.

For example, given the 2D grid:
INF  -1  0  INF
INF INF INF  -1
INF  -1 INF  -1
  0  -1 INF INF
 After running your function, the 2D grid should be:
  3  -1   0   1
  2   2   1  -1
  1  -1   2  -1
  0  -1   3   4

An application of BFS. The key is to apply appropriate pruning
http://buttercola.blogspot.com/2015/09/leetcode-walls-and-gates.html
It is very classic backtracking problem. We can start from each gate (0 point), and searching for its neighbors. We can either use DFS or BFS solution.
http://shibaili.blogspot.com/2015/09/day-130-286-expression-add-operators.html
Interview - What may change, explain and
Make code readable, extendable.
Pass a direction array. {-1, 1} etc
http://algobox.org/walls-and-gates/
The performances of MultiEnd and Naive BFS are very stable and have time complexities of O(n^2) for a n x n square matrix.
The performance of recursive DFS is very unstable. It is much slower than BFS if the rooms are interconnected. It is only faster than BFS when small groups of rooms are isolated.
Thus, for this problem we should prefer BFS over DFS. And the best Solution is Multi End BFS.
DFS is much slower than BFS. DFS is repeatedly updating the cell distance. Since there is only one gate in this case, NaiveBFS is expected to perform just like the MultiEndBFS.

X. BFS
http://segmentfault.com/a/1190000003906674
实际上就是找每个房间到最近的门的距离,我们从每个门开始,广度优先搜索并记录层数就行了。如果某个房间之前被标记过距离,那就选择这个距离和当前距离中较小的那个。这题要注意剪枝,如果下一步是门或者下一步是墙或者下一步已经访问过了,就不要加入队列中。否则会超时。

Don't need the visisted hashset.
    public void wallsAndGates(int[][] rooms) {
        if(rooms.length == 0) return;
        for(int i = 0; i < rooms.length; i++){
            for(int j = 0; j < rooms[0].length; j++){
                // 如果遇到一个门,从门开始广度优先搜索,标记连通的节点到自己的距离
                if(rooms[i][j] == 0) bfs(rooms, i, j);
            }
        }
    }
    
    public void bfs(int[][] rooms, int i, int j){
        Queue<Integer> queue = new LinkedList<Integer>();
        queue.offer(i * rooms[0].length + j);
        int dist = 0;
        // 用一个集合记录已经访问过的点
        Set<Integer> visited = new HashSet<Integer>();
        visited.add(i * rooms[0].length + j);
        while(!queue.isEmpty()){
            int size = queue.size();
            // 记录深度的搜索
            for(int k = 0; k < size; k++){
                Integer curr = queue.poll();
                int row = curr / rooms[0].length;
                int col = curr % rooms[0].length;
                // 选取之前标记的值和当前的距离的较小值
                rooms[row][col] = Math.min(rooms[row][col], dist);
                int up = (row - 1) * rooms[0].length + col;
                int down = (row + 1) * rooms[0].length + col;
                int left = row * rooms[0].length + col - 1;
                int right = row * rooms[0].length + col + 1;
                if(row > 0 && rooms[row - 1][col] > 0 && !visited.contains(up)){
                    queue.offer(up);
                    visited.add(up);
                }
                if(col > 0 && rooms[row][col - 1] > 0 && !visited.contains(left)){
                    queue.offer(left);
                    visited.add(left);
                }
                if(row < rooms.length - 1 && rooms[row + 1][col] > 0 && !visited.contains(down)){
                    queue.offer(down);
                    visited.add(down);
                }
                if(col < rooms[0].length - 1 && rooms[row][col + 1] > 0 && !visited.contains(right)){
                    queue.offer(right);
                    visited.add(right);
                }
            }
            dist++;
        }
    }
http://algobox.org/walls-and-gates/
https://leetcode.com/discuss/82264/benchmarks-of-dfs-and-bfs
The performances of MultiEnd is very stable and have time complexities of O(n^2) for a n x nsquare matrix.
The time complexity for NaiveBFS should be O(n^4) in the worst case. However is not shown in our tests.
The performance of recursive DFS is very unstable. It is much slower than BFS if the rooms are interconnected. It is only faster than BFS when small groups of rooms are isolated. In the worst case the time complexity is also O(n^4).
Thus, for this problem we should prefer BFS over DFS. And the best Solution is Multi End BFS.

Because in the worst case, we can have O(n^2) gates. For example 1/4n^2. For each gate, DFS will need to travel n^2 to 1 rooms, thus total O(n^4).
A visited matrix is not necessary. Firstly, because rooms matrix contains this information; Secondly, and mainly, because DFS need to revisit a cell even if it is already visited by other gates to update the cell to the minimum distance.
And that is exactly why the time complexity of DFS in the worst case can be O(n^4).

    public static final int[] d = {0, 1, 0, -1, 0};
    public void wallsAndGates(int[][] rooms) {
        if (rooms.length == 0) return;
        for (int i = 0; i < rooms.length; ++i)
            for (int j = 0; j < rooms[0].length; ++j)
                if (rooms[i][j] == 0) bfs(rooms, i, j);
    }
    private void bfs(int[][] rooms, int i, int j) {
        int m = rooms.length, n = rooms[0].length;
        Deque<Integer> queue = new ArrayDeque<>();
        queue.offer(i * n + j); // Put gate in the queue
        while (!queue.isEmpty()) {
            int x = queue.poll();
            i = x / n; j = x % n;
            for (int k = 0; k < 4; ++k) {
                int p = i + d[k], q = j + d[k + 1];
                if (0 <= p && p < m && 0 <= q && q < n && rooms[p][q] > rooms[i][j] + 1) {
                    rooms[p][q] = rooms[i][j] + 1;
                    queue.offer(p * n + q);
                }
            }
        }
    }
X. Java(Multi End BFS)
https://leetcode.com/discuss/60179/java-bfs-solution-o-mn-time
Push all gates into queue first. Then for each gate update its neighbor cells and push them to the queue.
Repeating above steps until there is nothing left in the queue.
public class Solution { public void wallsAndGates(int[][] rooms) { LinkedList<int[]> list = new LinkedList<int[]>(); for(int i = 0; i < rooms.length; i++) { for(int j = 0; j < rooms[0].length; j++) { if(rooms[i][j] == 0) list.add(new int[]{i,j}); } } int[][] diff = new int[][]{{-1,0,1,0},{0,1,0,-1}}; while(!list.isEmpty()) { int[] pop = list.remove(); for(int i = 0; i < diff[0].length; i++) { int newR = pop[0] + diff[0][i]; int newC = pop[1] + diff[1][i]; if(newR < 0 || newR >= rooms.length || newC < 0 || newC >= rooms[0].length || rooms[newR][newC] != Integer.MAX_VALUE) continue; rooms[newR][newC] = rooms[pop[0]][pop[1]] + 1; list.add(new int[]{newR, newC}); } } }


    public static final int[] d = {0, 1, 0, -1, 0};
    public void wallsAndGates(int[][] rooms) {
        if (rooms.length == 0) return;
        int m = rooms.length, n = rooms[0].length;
        Deque<Integer> queue = new ArrayDeque<>();
        for (int i = 0; i < m; ++i)
            for (int j = 0; j < n; ++j)
                if (rooms[i][j] == 0) queue.offer(i * n + j); // Put gates in the queue
        while (!queue.isEmpty()) {
            int x = queue.poll();
            int i = x / n, j = x % n;
            for (int k = 0; k < 4; ++k) {
                int p = i + d[k], q = j + d[k + 1]; // empty room
                if (0 <= p && p < m && 0 <= q && q < n &&
                    rooms[p][q] == Integer.MAX_VALUE) {
                    rooms[p][q] = rooms[i][j] + 1;
                    queue.offer(p * n + q);
                }
            }
        }

    }

找出所有的gate,然后同时bfs
http://buttercola.blogspot.com/2015/09/leetcode-walls-and-gates.html
    public void wallsAndGates(int[][] rooms) {
        if (rooms == null || rooms.length == 0) {
            return;
        }
         
        int m = rooms.length;
        int n = rooms[0].length;
         
        Queue<Integer> queue = new LinkedList<>();
        for (int i = 0; i < m; i++) {
            for (int j = 0; j < n; j++) {
                if (rooms[i][j] == 0) {
                    wallsAndGatesHelper(i, j, 0, rooms, queue);
                }
            }
        }
    }
     
    private void wallsAndGatesHelper(int row, int col, int distance, int[][] rooms, Queue<Integer> queue) {
        fill(row, col, distance, rooms, queue);
         
        int m = rooms.length;
        int n = rooms[0].length;
         
        while (!queue.isEmpty()) {
            int size = queue.size();
            for (int i = 0; i < size; i++) {
                int cord = queue.poll();
                int x = cord / n;
                int y = cord % n;
             
                fill(x - 1, y, distance + 1, rooms, queue);
                fill(x + 1, y, distance + 1, rooms, queue);
                fill(x, y - 1, distance + 1, rooms, queue);
                fill(x, y + 1, distance + 1, rooms, queue);
             
            }
            distance++;
        }
    }
     
    private void fill (int row, int col, int distance, int[][] rooms, Queue<Integer> queue) {
        int m = rooms.length;
        int n = rooms[0].length;
         
        if (row < 0 || row >= m || col < 0 || col >= n) {
            return;
        }
         
        if (rooms[row][col] == -1) {
            return;
        }
         
        if (distance > rooms[row][col]) {
            return;
        }
         
        if (distance < rooms[row][col]) {
            rooms[row][col] = distance;
        }
         
        int cord = row * n + col;
        queue.offer(cord);
    }



    void wallsAndGates(vector<vector<int>>& rooms) {
        int m = rooms.size();
        if (m == 0) return;
        int n = rooms[0].size();
        queue<pair<int,int>> que;
         
        for (int i = 0; i < m; i++) {
            for (int j = 0; j < n; j++) {
                if (rooms[i][j] == 0) {
                    que.push(make_pair(i,j));
                }
            }
        }
         
        int size = que.size();
        int dis = 1;
        while (!que.empty()) {
            int row = que.front().first;
            int col = que.front().second;
            size--;
            que.pop();
            
            if (row + 1 < m && rooms[row + 1][col] > dis) {
                rooms[row + 1][col] = dis;
                que.push(make_pair(row + 1,col));
            }
            if (row - 1 >= 0 && rooms[row - 1][col] > dis) {
                rooms[row - 1][col] = dis;
                que.push(make_pair(row - 1,col));
            }
            if (col + 1 < n && rooms[row][col + 1] > dis) {
                rooms[row][col + 1] = dis;
                que.push(make_pair(row,col + 1));
            }
            if (col - 1 >= 0 && rooms[row][col - 1] > dis) {
                rooms[row][col - 1] = dis;
                que.push(make_pair(row,col - 1));
            }
             
            if (size == 0) {
                size = que.size();
                dis++;
            }
        }
    }
X. BFS + Pruning
http://tiancao.me/Leetcode-Unlocked/LeetCode%20Locked/c1.24.html
    void wallsAndGates(vector<vector<int>>& rooms) {
        if (rooms.empty()) return;
        int m = rooms.size(), n = rooms[0].size();
        queue<pair<int, int>> q;
        for (int i = 0; i < m; i++) {
            for (int j = 0; j < n; j++) {
                if (!rooms[i][j]) q.push({i, j});
            }
        }

        for (int d = 1; !q.empty(); d++) {
            for (int k = q.size(); k; k--) {
                int i = q.front().first, j = q.front().second;
                q.pop();
                add(rooms, q, i - 1, j, m, n, d);
                add(rooms, q, i + 1, j, m, n, d);
                add(rooms, q, i, j - 1, m, n, d);
                add(rooms, q, i, j + 1, m, n, d);
            }
        }
    }
private:
    void add(vector<vector<int>> &rooms, queue<pair<int, int>> &q, int i, int j, int m, int n, int d) {
        if (i >= 0 && i < m && j >= 0 && j < n && rooms[i][j] > d) {
            q.push({i, j});
            rooms[i][j] = d;
        }
    }
2 public:
 3     void wallsAndGates(vector<vector<int>>& rooms) {
 4         if (rooms.empty()) return;
 5         int m = rooms.size(), n = rooms[0].size();
 6         for (int i = 0; i < m; i++) {
 7             for (int j = 0; j < n; j++) {
 8                 if (!rooms[i][j]) {
 9                     queue<Grid> grids;
10                     grids.push(Grid(i + 1, j, 1));
11                     grids.push(Grid(i - 1, j, 1));
12                     grids.push(Grid(i, j + 1, 1));
13                     grids.push(Grid(i, j - 1, 1));
14                     while (!grids.empty()) {
15                         Grid grid = grids.front();
16                         grids.pop();
17                         int r = grid.r, c = grid.c, d = grid.d;
18                         if (r < 0 || r >= m || c < 0 || c >= n || rooms[r][c] < d)
19                             continue;
20                         rooms[r][c] = d;
21                         grids.push(Grid(r + 1, c, d + 1));
22                         grids.push(Grid(r - 1, c, d + 1));
23                         grids.push(Grid(r, c + 1, d + 1));
24                         grids.push(Grid(r, c - 1, d + 1));
25                     }
26                 }
27             }
28         }
29     }
30 private:
31     struct Grid {
32         int r, c, d;
33         Grid(int _r, int _c, int _d) : r(_r), c(_c), d(_d) {}
34     };

3     void wallsAndGates(vector<vector<int>>& rooms) {
 4         int m = rooms.size(), n = m ? rooms[0].size() : 0;
 5         queue<pair<int, int>> q;
 6         for (int i = 0; i < m; i++)
 7             for (int j = 0; j < n; j++)
 8                 if (!rooms[i][j]) q.push({i, j});
 9         for (int d = 1; !q.empty(); d++) {
10             for (int k = q.size(); k; k--) {
11                 int i = q.front().first, j = q.front().second;
12                 q.pop();
13                 add(rooms, q, i - 1, j, m, n, d);
14                 add(rooms, q, i + 1, j, m, n, d);
15                 add(rooms, q, i, j - 1, m, n, d);
16                 add(rooms, q, i, j + 1, m, n, d); 
17             }
18         }
19     }
20 private:
21     void add(vector<vector<int>>& rooms, queue<pair<int, int>>& q, int i, int j, int m, int n, int d) {
22         if (i >= 0 && i < m && j >= 0 && j < n && rooms[i][j] > d) {
23             q.push({i, j});
24             rooms[i][j] = d;
25         }
26     }

X. DFS  
https://leetcode.com/discuss/78333/my-short-java-solution-very-easy-to-understand
Use origin input as visited[][]
I think it should be O(kmn) where k is the number of 0.
I think time complexity should be O(mn) since each entry will be visited at most 4 times which means O(4mn)
public void wallsAndGates(int[][] rooms) {
    for (int i = 0; i < rooms.length; i++)
        for (int j = 0; j < rooms[0].length; j++)
            if (rooms[i][j] == 0) helper(rooms, i, j, 0);
}

private void helper(int[][] rooms, int i, int j, int d) {
    if (i < 0 || i >= rooms.length || j < 0 || j >= rooms[0].length || rooms[i][j] < d) return;
    rooms[i][j] = d;
    helper(rooms, i - 1, j, d + 1);
    helper(rooms, i + 1, j, d + 1);
    helper(rooms, i, j - 1, d + 1);
    helper(rooms, i, j + 1, d + 1);
}
http://blog.csdn.net/xudli/article/details/48748547
    public void wallsAndGates(int[][] rooms) {
        if(rooms==null || rooms.length==0 || rooms[0]==null || rooms[0].length==0) return;
        int m = rooms.length;
        int n =rooms[0].length;        
        boolean[][] visited = new boolean[m][n];
        
        for(int i=0; i<m; i++) {
            for(int j=0; j<n; j++) {
                if(rooms[i][j] == Integer.MAX_VALUE) {
                    rooms[i][j] = search(rooms, visited, i, j, m, n);
                }
            }
        }
        return;
    }
    
    private int search(int[][] rooms, boolean[][] visited, int i, int j, int m, int n) {
        if(i<0 || i>m-1 || j<0 || j>n-1 || rooms[i][j] == -1) return Integer.MAX_VALUE;
        if(rooms[i][j]==0) return 0;
        if(visited[i][j]) return rooms[i][j];
        visited[i][j] = true;
        
        if(rooms[i][j]>0 && rooms[i][j]<Integer.MAX_VALUE) return rooms[i][j];        
        int up = search(rooms, visited, i-1, j, m, n);
        int down = search(rooms, visited, i+1, j, m, n);
        int left = search(rooms, visited, i, j-1, m, n);
        int right = search(rooms, visited, i, j+1, m, n);
        
        visited[i][j] = false;
        
        int min = Math.min( Math.min(up, down), Math.min(left, right) );
        return min==Integer.MAX_VALUE ? min : min+1;
    }
http://buttercola.blogspot.com/2015/09/leetcode-walls-and-gates.html
    public void wallsAndGates(int[][] rooms) {
        if (rooms == null || rooms.length == 0) {
            return;
        }
         
        int m = rooms.length;
        int n = rooms[0].length;
         
        boolean[][] visited = new boolean[m][n];
         
        for (int i = 0; i < m; i++) {
            for (int j = 0; j < n; j++) {
                if (rooms[i][j] == 0) {
                    wallsAndGatesHelper(i, j, 0, visited, rooms);
                }
            }
        }
    }
     
    private void wallsAndGatesHelper(int row, int col, int distance, boolean[][] visited, int[][] rooms) {
        int rows = rooms.length;
        int cols = rooms[0].length;
         
        if (row < 0 || row >= rows || col < 0 || col >= cols) {
            return;
        }
         
        // visited
        if (visited[row][col]) {
            return;
        }
         
        // Is wall?
        if (rooms[row][col] == -1) {
            return;
        }
         
        // Distance greater than current
        if (distance > rooms[row][col]) {
            return;
        }
         
         
        // Mark as visited
        visited[row][col] = true;
         
        if (distance < rooms[row][col]) {
            rooms[row][col] = distance;
        }
         
        // go up, down, left and right
        wallsAndGatesHelper(row - 1, col, distance + 1, visited, rooms);
        wallsAndGatesHelper(row + 1, col, distance + 1, visited, rooms);
        wallsAndGatesHelper(row, col - 1, distance + 1, visited, rooms);
        wallsAndGatesHelper(row, col + 1, distance + 1, visited, rooms);
         
        // Mark as unvisited
        visited[row][col] = false;
    }
http://likemyblogger.blogspot.com/2015/09/leetcode-286-walls-and-gates.html
    void wallsAndGates(vector<vector<int>>& rooms) {
        int m = rooms.size();
        if(m==0) return;
        int n = rooms[0].size();
        if(n==0) return;
         
        for(int i=0; i<m; ++i){
            for(int j=0; j<n; ++j){
                stack<pair<int, int>> stk;
                if(rooms[i][j]==0){
                    stk.push(pair<int, int>(i,j));
                    while(!stk.empty()){
                        int x = stk.top().first, y = stk.top().second;
                        stk.pop();
                        if(x-1>=0 && rooms[x-1][y]>rooms[x][y]+1){rooms[x-1][y] = rooms[x][y]+1; stk.push(pair<int, int>(x-1,y));}
                        if(x+1<m  && rooms[x+1][y]>rooms[x][y]+1){rooms[x+1][y] = rooms[x][y]+1; stk.push(pair<int, int>(x+1,y));}
                        if(y-1>=0 && rooms[x][y-1]>rooms[x][y]+1){rooms[x][y-1] = rooms[x][y]+1; stk.push(pair<int, int>(x,y-1));}
                        if(y+1<n  && rooms[x][y+1]>rooms[x][y]+1){rooms[x][y+1] = rooms[x][y]+1; stk.push(pair<int, int>(x,y+1));}
                    }
                }
            }
        }
    }

Time complexity:
https://leetcode.com/discuss/61429/little-bit-confused-about-the-time-complexity-here
It is really O(mn). Image each gate as the root of a tree, the queue could magically guarantee we traverse level by level of each trees.
step 1: add each root node into the queue.
step 2: pop a node(root) out, visit it is 1st level children(if has not been visited), add all 1st level children into the queue. then pop second node(root) out ...


https://discuss.leetcode.com/topic/176/calculate-minimum-path-from-a-given-point-i-j-to-point-x-y-in-a-martix/8
with BFS complexity is O(E+V), we have mn4 E maximum (in case there are 0 blocks) and m*n vertexes.
Why is complexity exponential? We can also run two BFS simultaneosuly from both point and the first point they meet ,we stop

with BFS you find the minimum path without trying all possibilities, as you do with DFS. I don't see any sense to traverse deep in the graph when you need to find minimum distance to the point

变形:给你⼀一个board,上⾯面有三种类型的点,第⼀一种是空位,第⼆二种是
obstacle,第三种是猫。如果你是⽼老老⿏鼠,你想离猫越远越好,应该待在哪
个/些点上。输出全部这些点。

Labels

LeetCode (1432) GeeksforGeeks (1122) LeetCode - Review (1067) Review (882) Algorithm (668) to-do (609) Classic Algorithm (270) Google Interview (237) Classic Interview (222) Dynamic Programming (220) DP (186) Bit Algorithms (145) POJ (141) Math (137) Tree (132) LeetCode - Phone (129) EPI (122) Cracking Coding Interview (119) DFS (115) Difficult Algorithm (115) Lintcode (115) Different Solutions (110) Smart Algorithm (104) Binary Search (96) BFS (91) HackerRank (90) Binary Tree (86) Hard (79) Two Pointers (78) Stack (76) Company-Facebook (75) BST (72) Graph Algorithm (72) Time Complexity (69) Greedy Algorithm (68) Interval (63) Company - Google (62) Geometry Algorithm (61) Interview Corner (61) LeetCode - Extended (61) Union-Find (60) Trie (58) Advanced Data Structure (56) List (56) Priority Queue (53) Codility (52) ComProGuide (50) LeetCode Hard (50) Matrix (50) Bisection (48) Segment Tree (48) Sliding Window (48) USACO (46) Space Optimization (45) Company-Airbnb (41) Greedy (41) Mathematical Algorithm (41) Tree - Post-Order (41) ACM-ICPC (40) Algorithm Interview (40) Data Structure Design (40) Graph (40) Backtracking (39) Data Structure (39) Jobdu (39) Random (39) Codeforces (38) Knapsack (38) LeetCode - DP (38) Recursive Algorithm (38) String Algorithm (38) TopCoder (38) Sort (37) Introduction to Algorithms (36) Pre-Sort (36) Beauty of Programming (35) Must Known (34) Binary Search Tree (33) Follow Up (33) prismoskills (33) Palindrome (32) Permutation (31) Array (30) Google Code Jam (30) HDU (30) Array O(N) (29) Logic Thinking (29) Monotonic Stack (29) Puzzles (29) Code - Detail (27) Company-Zenefits (27) Microsoft 100 - July (27) Queue (27) Binary Indexed Trees (26) TreeMap (26) to-do-must (26) 1point3acres (25) GeeksQuiz (25) Merge Sort (25) Reverse Thinking (25) hihocoder (25) Company - LinkedIn (24) Hash (24) High Frequency (24) Summary (24) Divide and Conquer (23) Proof (23) Game Theory (22) Topological Sort (22) Lintcode - Review (21) Tree - Modification (21) Algorithm Game (20) CareerCup (20) Company - Twitter (20) DFS + Review (20) DP - Relation (20) Brain Teaser (19) DP - Tree (19) Left and Right Array (19) O(N) (19) Sweep Line (19) UVA (19) DP - Bit Masking (18) LeetCode - Thinking (18) KMP (17) LeetCode - TODO (17) Probabilities (17) Simulation (17) String Search (17) Codercareer (16) Company-Uber (16) Iterator (16) Number (16) O(1) Space (16) Shortest Path (16) itint5 (16) DFS+Cache (15) Dijkstra (15) Euclidean GCD (15) Heap (15) LeetCode - Hard (15) Majority (15) Number Theory (15) Rolling Hash (15) Tree Traversal (15) Brute Force (14) Bucket Sort (14) DP - Knapsack (14) DP - Probability (14) Difficult (14) Fast Power Algorithm (14) Pattern (14) Prefix Sum (14) TreeSet (14) Algorithm Videos (13) Amazon Interview (13) Basic Algorithm (13) Codechef (13) Combination (13) Computational Geometry (13) DP - Digit (13) LCA (13) LeetCode - DFS (13) Linked List (13) Long Increasing Sequence(LIS) (13) Math-Divisible (13) Reservoir Sampling (13) mitbbs (13) Algorithm - How To (12) Company - Microsoft (12) DP - Interval (12) DP - Multiple Relation (12) DP - Relation Optimization (12) LeetCode - Classic (12) Level Order Traversal (12) Prime (12) Pruning (12) Reconstruct Tree (12) Thinking (12) X Sum (12) AOJ (11) Bit Mask (11) Company-Snapchat (11) DP - Space Optimization (11) Dequeue (11) Graph DFS (11) MinMax (11) Miscs (11) Princeton (11) Quick Sort (11) Stack - Tree (11) 尺取法 (11) 挑战程序设计竞赛 (11) Coin Change (10) DFS+Backtracking (10) Facebook Hacker Cup (10) Fast Slow Pointers (10) HackerRank Easy (10) Interval Tree (10) Limited Range (10) Matrix - Traverse (10) Monotone Queue (10) SPOJ (10) Starting Point (10) States (10) Stock (10) Theory (10) Tutorialhorizon (10) Kadane - Extended (9) Mathblog (9) Max-Min Flow (9) Maze (9) Median (9) O(32N) (9) Quick Select (9) Stack Overflow (9) System Design (9) Tree - Conversion (9) Use XOR (9) Book Notes (8) Company-Amazon (8) DFS+BFS (8) DP - States (8) Expression (8) Longest Common Subsequence(LCS) (8) One Pass (8) Quadtrees (8) Traversal Once (8) Trie - Suffix (8) 穷竭搜索 (8) Algorithm Problem List (7) All Sub (7) Catalan Number (7) Cycle (7) DP - Cases (7) Facebook Interview (7) Fibonacci Numbers (7) Flood fill (7) Game Nim (7) Graph BFS (7) HackerRank Difficult (7) Hackerearth (7) Inversion (7) Kadane’s Algorithm (7) Manacher (7) Morris Traversal (7) Multiple Data Structures (7) Normalized Key (7) O(XN) (7) Radix Sort (7) Recursion (7) Sampling (7) Suffix Array (7) Tech-Queries (7) Tree - Serialization (7) Tree DP (7) Trie - Bit (7) 蓝桥杯 (7) Algorithm - Brain Teaser (6) BFS - Priority Queue (6) BFS - Unusual (6) Classic Data Structure Impl (6) DP - 2D (6) DP - Monotone Queue (6) DP - Unusual (6) DP-Space Optimization (6) Dutch Flag (6) How To (6) Interviewstreet (6) Knapsack - MultiplePack (6) Local MinMax (6) MST (6) Minimum Spanning Tree (6) Number - Reach (6) Parentheses (6) Pre-Sum (6) Probability (6) Programming Pearls (6) Rabin-Karp (6) Reverse (6) Scan from right (6) Schedule (6) Stream (6) Subset Sum (6) TSP (6) Xpost (6) n00tc0d3r (6) reddit (6) AI (5) Abbreviation (5) Anagram (5) Art Of Programming-July (5) Assumption (5) Bellman Ford (5) Big Data (5) Code - Solid (5) Code Kata (5) Codility-lessons (5) Coding (5) Company - WMware (5) Convex Hull (5) Crazyforcode (5) DFS - Multiple (5) DFS+DP (5) DP - Multi-Dimension (5) DP-Multiple Relation (5) Eulerian Cycle (5) Graph - Unusual (5) Graph Cycle (5) Hash Strategy (5) Immutability (5) Java (5) LogN (5) Manhattan Distance (5) Matrix Chain Multiplication (5) N Queens (5) Pre-Sort: Index (5) Quick Partition (5) Quora (5) Randomized Algorithms (5) Resources (5) Robot (5) SPFA(Shortest Path Faster Algorithm) (5) Shuffle (5) Sieve of Eratosthenes (5) Strongly Connected Components (5) Subarray Sum (5) Sudoku (5) Suffix Tree (5) Swap (5) Threaded (5) Tree - Creation (5) Warshall Floyd (5) Word Search (5) jiuzhang (5)

Popular Posts