LeetCode79 Word Search

Given a 2D board and a word, find if the word exists in the grid.

The word can be constructed from letters of sequentially adjacent cell, where “adjacent” cells are those horizontally or vertically neighboring. The same letter cell may not be used more than once.
Example:

board =
[
[‘A’,‘B’,‘C’,‘E’],
[‘S’,‘F’,‘C’,‘S’],
[‘A’,‘D’,‘E’,‘E’]
]
Given word = “ABCCED”, return true.
Given word = “SEE”, return true.
Given word = “ABCB”, return false.

這道題,一看就是DFS,但是我的DFS掌握的不是很好,所以在這裏記錄一下。
一開始,我是這樣寫的代碼:

class Solution {
    private int[][] directions = {{1,0} , {-1,0} , {0,1} , {0,-1}};
    private int m,n;
    public boolean exist(char[][] board, String word) {
        m = board.length;
        n = board[0].length;
        boolean res = false;
        boolean[][] visited = new boolean[m][n];
        for(int i = 0 ; i < board.length ; i++) {
            for(int j = 0 ; j < board[0].length ; j++) {
                if(board[i][j] == word.charAt(0)) {
                    res = res || helper(board , word , i , j , visited , 0);
                    if(res) return true; 
                }
            }
        }
        return false;
    }
    
    private boolean helper(char[][] board , String word , int r , int c ,boolean[][] visited , int k) {
        if(r < 0 || r >= m || c < 0 || c >= n || visited[r][c] || board[r][c] != word.charAt(k) ) return false;
        if(k == word.length()-1) return true;
        visited[r][c] = true;
        boolean res = false;
        for(int[] d : directions) {
            int nextX = r + d[0];
            int nextY = c + d[1];
            res = res || helper(board,word,nextX,nextY,visited,k+1); 
        }
        return res;
    }
}

這樣寫是錯的,錯的原因主要在visited。帶入下面的例子就知道了

[["C","A","A"],["A","A","A"],["B","C","D"]]
"AAB"

後來改正代碼,如下

class Solution {
    private int[][] directions = {{1,0} , {-1,0} , {0,1} , {0,-1}};
    private int m,n;
    public boolean exist(char[][] board, String word) {
        m = board.length;
        n = board[0].length;
        boolean res = false;
        boolean[][] visited = new boolean[m][n];
        for(int i = 0 ; i < board.length ; i++) {
            for(int j = 0 ; j < board[0].length ; j++) {
                if(helper(board , word , i , j , visited , 0)) {
                    return true;
                }
            }
        }
        return false;
    }
    
    private boolean helper(char[][] board , String word , int r , int c ,boolean[][] visited , int k) {
        if(k == word.length()) return true;
        if(r < 0 || r >= m || c < 0 || c >= n || visited[r][c] || board[r][c] != word.charAt(k) ) return false;
        
        visited[r][c] = true;
        
        for(int[] d : directions) {
            int nextX = r + d[0];
            int nextY = c + d[1];
            if(helper(board,word,nextX,nextY,visited,k+1)) return true;
        }
        
        visited[r][c] = false;
        return false;
    }
}

這樣子就對了。visited[r][c]只有在走的過程中爲ture纔會被標記爲true,否則就會被標記爲false,不然這會影響下一次的判斷。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章