leetcode 542. 01 Matrix 、663. Walls and Gates(lintcode) 、773. Sliding Puzzle 、803. Shortest Distance

542. 01 Matrixhtml

https://www.cnblogs.com/grandyang/p/6602288.htmlui

將全部的1置爲INT_MAX,而後用全部的0去更新本來位置爲1的值。spa

最短距離確定使用bfs。code

每次更新了值的地方還要再加入隊列中 。htm

class Solution {
public:
    vector<vector<int>> updateMatrix(vector<vector<int>>& matrix) {
        int m = matrix.size(),n = matrix[0].size();
        queue<pair<int,int>> q;
        for(int i = 0;i < m;i++){
            for(int j = 0;j < n;j++){
                if(matrix[i][j] == 0)
                    q.push(make_pair(i,j));
                else
                    matrix[i][j] = INT_MAX;
            }
        }
        while(!q.empty()){
            auto coordinate = q.front();
            q.pop();
            int x = coordinate.first,y = coordinate.second;
            for(auto dir : dirs){
                int new_x = x + dir[0];
                int new_y = y + dir[1];
                if(new_x < 0 || new_x >= matrix.size() || new_y < 0 || new_y >= matrix[0].size() || matrix[new_x][new_y] <= matrix[x][y] + 1)
                    continue;
                matrix[new_x][new_y] = matrix[x][y] + 1;
                q.push(make_pair(new_x,new_y));
            }
        }
        return matrix;
    }
private:
    vector<vector<int>> dirs{{-1,0},{1,0},{0,-1},{0,1}};
};

 

663. Walls and Gatesblog

https://www.cnblogs.com/grandyang/p/5285868.html隊列

這個題跟542. 01 Matrix很像,主要利用bfs。先把全部的0位置放入隊列中,而後經過0更新周圍的位置達到更新全部的位置。it

class Solution {
public:
    /**
     * @param rooms: m x n 2D grid
     * @return: nothing
     */
    void wallsAndGates(vector<vector<int>> &rooms) {
        // write your code here
        queue<pair<int,int>> q;
        for(int i = 0;i < rooms.size();i++){
            for(int j = 0;j < rooms[0].size();j++){
                if(rooms[i][j] == 0)
                    q.push(make_pair(i,j));
            }
        }
        while(!q.empty()){
            int x = q.front().first;
            int y = q.front().second;
            q.pop();
            for(auto dir : dirs){
                int x_new = x + dir[0];
                int y_new = y + dir[1];
                if(x_new < 0 || x_new >= rooms.size() || y_new < 0 || y_new >= rooms[0].size() || rooms[x_new][y_new] < rooms[x][y] + 1)
                    continue;
                rooms[x_new][y_new] = rooms[x][y] + 1;
                q.push(make_pair(x_new,y_new));
            }
        }
        return;
    }
private:
    vector<vector<int>> dirs{{-1,0},{1,0},{0,-1},{0,1}};
};

 

773. Sliding Puzzleio

https://www.cnblogs.com/grandyang/p/8955735.htmlclass

queue裏面存儲的是每次變換後的board的樣子和當前新的board中0所在的座標。

將隊列一次清空完了以後才能更新res,由於這就是一次變換。

用set至關於決定何時中止循環

class Solution {
public:
    int slidingPuzzle(vector<vector<int>>& board) {
        int res = 0,m = board.size(),n = board[0].size();
        set<vector<vector<int>>> visited;
        vector<vector<int>> correct{{1,2,3},{4,5,0}};
        queue<pair<vector<vector<int>>,vector<int>>> q;
        for(int i = 0;i < m;i++){
            for(int j = 0;j < n;j++){
                if(board[i][j] == 0){
                    vector<int> tmp;
                    tmp.push_back(i);
                    tmp.push_back(j);
                    q.push(make_pair(board,tmp));
                }
            }
        }
        while(!q.empty()){
            for(int i = q.size();i > 0;i--){
                int x = q.front().second[0];
                int y = q.front().second[1];
                vector<vector<int>> board_new = q.front().first;
                if(board_new == correct)
                    return res;
                visited.insert(board_new);
                q.pop();
                for(auto dir : dirs){
                    int new_x = x + dir[0];
                    int new_y = y + dir[1];
                    if(new_x < 0 || new_x >= m || new_y < 0 || new_y >= n)
                        continue;
                    vector<vector<int>> cand = board_new;
                    swap(cand[x][y],cand[new_x][new_y]);
                    if(visited.find(cand) != visited.end())
                        continue;
                    vector<int> tmp;
                    tmp.push_back(new_x);
                    tmp.push_back(new_y);
                    q.push(make_pair(cand,tmp));
                }
            }
            res++;
        }
        return -1;
    }
private:
    vector<vector<int>> dirs{{-1,0},{1,0},{0,-1},{0,1}};
};

 

803. Shortest Distance from All Buildings

https://www.cnblogs.com/grandyang/p/5297683.html

到全部建築物的距離和最小,其實也就等於到每一個建築物最小距離的和。

以每一個建築物作bfs求最小的距離,而後用一個dis的vector保存,每當增長一個建築物,在相應位置疊加當前建築物的最小距離便可。

有可能有些點沒法訪問到某一些建築物,因此經過一個count矩陣存儲每一個位置能訪問到的建築物的個數,最後再判斷可否達到。

class Solution {
public:
    /**
     * @param grid: the 2D grid
     * @return: the shortest distance
     */
    int shortestDistance(vector<vector<int>> &grid) {
        // write your code here
        int m = grid.size(),n = grid[0].size();
        int res = INT_MAX,building = 0;
        vector<vector<int>> dist(m,vector<int>(n,0));
        vector<vector<int>> count = dist;
        for(int i = 0;i < m;i++){
            for(int j = 0;j < n;j++){
                if(grid[i][j] == 1){
                    building++;
                    queue<pair<int,int>> q;
                    vector<vector<bool>> visited(m,vector<bool>(n,false));
                    q.push(make_pair(i,j));
                    int pace = 0;
                    while(!q.empty()){
                        pace++;
                        for(int i = q.size();i > 0;i--){
                            int x = q.front().first;
                            int y = q.front().second;
                            q.pop();
                            for(auto dir : dirs){
                                int new_x = x + dir[0];
                                int new_y = y + dir[1];
                                if(new_x < 0 || new_x >= m || new_y < 0 || new_y >= n || visited[new_x][new_y]== true || grid[new_x][new_y] != 0)
                                    continue;
                                dist[new_x][new_y] += pace;
                                count[new_x][new_y] += 1;
                                visited[new_x][new_y] = true;
                                q.push(make_pair(new_x,new_y));
                            }
                        }
                    }
                }
            }
        }
        for(int i = 0;i < m;i++){
            for(int j = 0;j < n;j++){
                if(grid[i][j] == 0 && count[i][j] == building)
                    res = min(res,dist[i][j]);
            }
        }
        return res == INT_MAX ? -1 : res;
    }
private:
    vector<vector<int>> dirs{{-1,0},{1,0},{0,-1},{0,1}};
};
相關文章
相關標籤/搜索