title : Matrix Word Search
Difficulty : Medium
topic content :
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 is those horizontally or V Ertically neighboring. The same letter cell is used more than once.
translation :
Given a 2D character array and a word, find out if the word exists in the grid.
The word can be constructed by the alphabet of adjacent cells, where "adjacent" cells are horizontal or vertical adjacent. The same letter unit may 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.
My idea : Loop through the entire two-dimensional array, and for each letter enter a recursive method,
1. Judge if the current character does not match the first letter of the passed-in string, or if it has been accessed, returns Fasle;
2, this is the last character, returns true; (has already been matched by the above judgment)
3, the access character of this position is set 1, and then the recursive method is called up, down, left and right four directions respectively ;
4, Four direction access is complete, indicating that the path started at this point already has the result, the location accessor resets 0, and returns the "or" in four directions.
Why do we have to reset 0?
Because the entire recursive process has only one used Access flag matrix (reference type), if you set 1 after each access, no longer tube, then the path that has previously failed will have an impact on the path that was later accessed (for which the path is new).
The accessor class here used similar to the used used in the [47] topic permutations 2, but with different meanings,
Therefore, if there are included accessors in the recursion, the accessor should be set to 0 (or false) after the call recursion ends
My Code :
1 Public BooleanExistChar[] board, String word) {2 for(inti = 0; i < board.length; i++) {3 for(intj = 0; J < Board[0].length; J + +) {4 if(Find (Word, I, J, board,New int[Board.length] [Board[0].length])) {5 return true;6 }7 }8 }9 return false;Ten } One A Private BooleanFind (String Word,intIintJChar[] board,int[] used) { - if(I < 0 | | i > BOARD.LENGTH-1 | | J < 0 | | J > board[0].length-1) { - return false; the } - if(Board[i][j]! = Word.charat (0) | | used[i][j] = = 1) { - return false; -}Else if(word.length () = = 1) { + return true; - } +USED[I][J] = 1; A BooleanAns = Find (word.substring (1), i-1, J, board, used) at|| Find (word.substring (1), i+1, J, board, used) -|| Find (word.substring (1), I, j-1, board, used) -|| Find (word.substring (1), I, j+1, board, used); -USED[I][J] = 0; - returnans; -}
my complexity : O ((m*n) 2)
problems in the encoding process :
1, before the first is to determine the first letter is a match and then return directly to the results of the Find method, and later found that this is not possible, because if there is a previous match in front of the correct answer to the wrong answer, it will directly return the wrong answer false; —————— if True to return true, otherwise continue
2, before the flag is not taken into account, so that the path will look back; "" "A,a" "" "AAA"
3, before the use of four flags "Up-down-left-right", each time to determine whether the upper and lower left and right to make recursive calls, as follows:
if (i > 0) { = find (word.substring (1), I-1, J, board, used); }
And then finally to the four flag bit to perform or operation, but this path of the letter each will be four recursive, no short-circuit possible, so when the need for a method of multi-branch recursion, it is best to change to direct call method for short-circuit and or operation, This result is then added to the beginning of the method, which reduces the number of redundant operations. "Whether the subject will be able to go up and down the judgment added to the beginning of the recursive method"
4, this method can actually be optimized, that is, the characters visited by "*", in the end of the recursive set to the original value , so you can save a new flag matrix.
Answer code :
1 Public BooleanExistChar[] board, String word) {2 Char[] W =Word.tochararray ();3 for(inty=0; y<board.length; y++) {4 for(intx=0; x<board[y].length; X + +) {5 if(exist (board, Y, X, W, 0))return true;6 }7 }8 return false;9 }Ten One Private BooleanExistChar[] board,intYintXChar[] Word,inti) { A if(i = = word.length)return true; - if(y<0 | | x<0 | | y = board.length | | x = = board[y].length)return false; - if(board[y][x]! = Word[i])return false; theBOARD[Y][X] ^= 256; - Booleanexist = exist (board, Y, x+1, Word, i+1) -|| exist (board, Y, x-1, Word, i+1) -|| exist (board, y+1, X, Word, i+1) +|| exist (board, y-1, X, Word, i+1); -BOARD[Y][X] ^= 256; + returnexist; A}
Answer Ideas :
The basic idea is the same, but there are two highlights that are better than my approach:
1, using char[] and an int to indicate the current number of letters , instead of frequent use of substring to create a new string;
2, the use of binary operations and or the characteristics-- with or all 1, and or all 1 will be equal to their own , because the word is said to be the letter, and the letter is in 65~90,95~122, so with or 128 is also possible. So you don't have to use temp anymore.
Leetcode [79] (Java): Word Search (matrix word searching)