題目:數組
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']
]codeGiven word = "ABCCED", return true. Given word = "SEE", return true.
Given word = "ABCB", return false.字符串
這是一道搜索題,用backtracking作,問題就是怎樣設計這個回溯過程。
咱們須要的就是在這個二維數組裏面一個個尋找每一個字符,因此dfs的終止條件是當咱們把每一個字符所有搜索了,也就是index==word.length。由於每一個字符只能使用一次因此咱們還須要一個visited數組來記錄當前元素是否被訪問過,若是咱們找到了和當前搜索的字符相匹配的元素,咱們就要上下左右搜索四個方向。
這麼看來思路仍是很清晰的,可是我在作這一題時被幾點困擾:1.咱們須要遍歷二維數組,但同時咱們又須要移動移動被搜索字符串的index,一開始我是把遍歷二維數組和移動字符串的index寫在了同一個dfs的recursion裏面而後接下去我就沒辦法寫了,看了discuss以後才知道應該把遍歷二維數組寫在主函數裏面,讓它來調用dfs。2.選擇下一個能夠走的adjacent,我一開始還在想需不須要用一個list來存儲每一步能夠走的adjacent,這樣的話就太麻煩了,還須要分狀況討論,但實際上是沒有必要的。咱們把這些判斷都加在recursion的終止條件裏面就行了。it
代碼以下:io
class Solution { public boolean exist(char[][] board, String word) { int m = board.length, n = board[0].length; boolean[][] visited = new boolean[m][n]; for (int i = 0; i < board.length; i ++) { for (int j = 0; j < board[0].length; j ++) { if (word.charAt(0) == board[i][j] && dfs(board, word, visited, 0, i, j)) return true; } } return false; } public boolean dfs(char[][] board, String word, boolean[][] visited, int index, int row, int col) { if (index == word.length()) return true; if (row == board.length || row < 0 || col == board[0].length || col < 0 || visited[row][col] || word.charAt(index) != board[row][col]) return false; visited[row][col] = true; if (dfs(board, word, visited, index+1, row+1, col) || dfs(board, word, visited, index+1, row, col+1) || dfs(board, word, visited, index+1, row-1, col) || dfs(board, word, visited, index+1, row, col-1)) return true; visited[row][col] = false; return false; } }
這道題能夠對照37那道數獨題,收穫會更大。class