标签:分析 基本 false ring set 函数调用 oar point down
79题,
给你一个二维的board, 只能往上下左右四个方向走,为你是否能找到单词。
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.
分析: 算法并不难,从每个(i,j)为起点进行dfs, dfs 过程往上下左右四个方向走, 但不能走重复的节点,因此需要设置visted 来标记是否走过。
key point: 用visted 标记后,每次dfs 完后, 记得 visted 需要改成原来的value, 所谓的back tracking 就是体现在这里。
程序被我一开始写的太渣了:
class Solution { public boolean exist(char[][] board, String word) { int row = board[0].length; int col = board.length; boolean[][] visted = new boolean[col][row]; for(int i=0; i<col; i++){ for(int j=0; j<row; j++){ // System.out.println("start: "+ i+ " "+ j); if(dfs(i,j,board,visted,word,0)) return true; visted[i][j] = false; } } return false; } private boolean dfs(int i, int j, char[][] board, boolean[][] visted, String word, int depth){ if(board[i][j] != word.charAt(depth)) return false; if(depth == word.length()-1){ return true; } boolean flag = false; visted[i][j] = true; //System.out.println(i+ " "+ j); //System.out.println(depth); //up if(i-1>=0&& !visted[i-1][j]){ flag = flag || dfs(i-1,j,board,visted,word,depth+1); visted[i-1][j] = false; if(flag) return true; } //down if(i+1<board.length &&!visted[i+1][j]) { flag = flag || dfs(i+1,j,board,visted,word,depth+1); visted[i+1][j] = false; if(flag) return true; } //left if(j-1 >=0 && !visted[i][j-1]){ flag = flag || dfs(i,j-1,board,visted,word,depth+1); visted[i][j-1] = false; if(flag) return true; } //right if(j+1<board[0].length&& !visted[i][j+1]){ flag = flag || dfs(i,j+1,board,visted,word,depth+1); visted[i][j+1] = false; if(flag) return true; } return flag; } }
又改成了:
class Solution { public boolean exist(char[][] board, String word) { int row = board[0].length; int col = board.length; boolean[][] visted = new boolean[col][row]; for(int i=0; i<col; i++){ for(int j=0; j<row; j++){ // System.out.println("start: "+ i+ " "+ j); if(dfs(i,j,board,visted,word,0)) return true; // visted[i][j] = false; } } return false; } private boolean dfs(int i, int j, char[][] board, boolean[][] visted, String word, int depth){ if(board[i][j] != word.charAt(depth)) return false; if(depth == word.length()-1){ return true; } boolean flag = false; visted[i][j] = true; //System.out.println(i+ " "+ j); //System.out.println(depth); //up if(i-1>=0&& !visted[i-1][j]){ flag = flag || dfs(i-1,j,board,visted,word,depth+1); // visted[i-1][j] = false; } //down if(i+1<board.length &&!visted[i+1][j]) { flag = flag || dfs(i+1,j,board,visted,word,depth+1); // visted[i+1][j] = false; } //left if(j-1 >=0 && !visted[i][j-1]){ flag = flag || dfs(i,j-1,board,visted,word,depth+1); // visted[i][j-1] = false; } //right if(j+1<board[0].length&& !visted[i][j+1]){ flag = flag || dfs(i,j+1,board,visted,word,depth+1); // visted[i][j+1] = false; } visted[i][j] = false; return flag; } }
之所以写的不好,主要因为,应该把 边界条件和是否已经被访问 判断放在 下一次函数调用里,而不是本次里, 修改后的程序简单很多。
back traking 体现在 visted[i][j] = true ; dfs(...) ; visted[i][j] = false;
class Solution { public boolean exist(char[][] board, String word) { int row = board[0].length; int col = board.length; boolean[][] visted = new boolean[col][row]; for(int i=0; i<col; i++){ for(int j=0; j<row; j++){ if(dfs(i,j,board,visted,word,0)) return true; } } return false; } private boolean dfs(int i, int j, char[][] board, boolean[][] visted, String word, int depth){ if(i<0 || j<0 || i >=board.length || j>=board[0].length ) return false; if(board[i][j] != word.charAt(depth)) return false; if(visted[i][j]) return false; if(depth == word.length()-1){ return true; } visted[i][j] = true; boolean flag = dfs(i-1,j,board,visted,word,depth+1) ||dfs(i+1,j,board,visted,word,depth+1) || dfs(i,j-1,board,visted,word,depth+1)|| dfs(i,j+1,board,visted,word,depth+1); visted[i][j] = false; return flag; } }
212. Word Search II
和79 基本雷同,给你 一个 string[] words, 要你找出 words 符合 79题搜索条件的单词。
如果用 dfs, 在 79题基础上加个for 循环就好了。
但有个坑爹的地方: 字典: ["a"] words = ["a","a"] ,只能回 "a" ,而不能回 "a","a" 因此需要用set 存放结果。
更好的做法是用tier tree, 待续。
79. Word Search/212. Word Search II--图的back tracking -- tier tree 待续
标签:分析 基本 false ring set 函数调用 oar point down
原文地址:https://www.cnblogs.com/keepAC/p/9972760.html