摘要:題目解答這題我原來是在的基礎上,用來做的,代碼如下做完之后,結果運行是對的,但是了,所以肯定是有更好的辦法。代碼如下去重
題目:
Given a 2D board and a list of words from the dictionary, find all words in the board.
Each word must 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 in a word.
For example,
Given words = ["oath","pea","eat","rain"] and board =
[
["o","a","a","n"],
["e","t","a","e"],
["i","h","k","r"],
["i","f","l","v"]
]
Return ["eat","oath"].
解答:
這題我原來是在word search I的基礎上,用backtracking來做的,代碼如下:
public boolean exist(char[][] board, String word, int i, int j, int pos, boolean[][] visited) { if (pos == word.length()) return true; if (i < 0 || i > board.length - 1 || j < 0 || j > board[i].length - 1) return false; if (visited[i][j] || board[i][j] != word.charAt(pos)) return false; visited[i][j] = true; int[][] dir = {{-1, 0}, {1, 0}, {0, -1}, {0, 1}}; for (int k = 0; k < dir.length; k++) { int x = i + dir[k][0], y = j + dir[k][1]; if (exist(board, word, x, y, pos + 1, visited)) { return true; } } visited[i][j] = false; return false; } public boolean helper(char[][] board, String word) { boolean[][] visited = new boolean[board.length][board[0].length]; for (int i = 0; i < board.length; i++) { for (int j = 0; j < board[i].length; j++) { if (exist(board, word, i, j, 0, visited)) { return true; } } } return false; } public ListfindWords(char[][] board, String[] words) { List result = new ArrayList (); if (board == null || board.length == 0 || board[0].length == 0) return result; for (String word : words) { if (helper(board, word)) { if (!result.contains(word)) { result.add(word); } } } return result; }
做完之后,結果運行是對的,但是TLE了,所以肯定是有更好的辦法。在TLE的test case里,我看到是當prefix相同時,如果用backtracking那么會不斷地掃同一個位置的prefix,非常的冗余,那么怎么把prefix提取出來只掃一次呢?一個很好的辦法就是反過來,用trie樹先把單詞存起來,然后掃board,掃board的時候用trie樹中的可能出現的單詞作為限制條件,那么當掃到一個trie中結尾存在的單詞時,把它存進result中去。代碼如下:
class TrieNode { TrieNode[] next = new TrieNode[26]; String word; } public TrieNode buildTrie(String[] words) { TrieNode root = new TrieNode(); for (String word : words) { TrieNode p = root; for (char c : word.toCharArray()) { int i = c - "a"; if (p.next[i] == null) p.next[i] = new TrieNode(); p = p.next[i]; } p.word = word; } return root; } public void dfs(Listresult, char[][] board, TrieNode p, int i, int j) { char c = board[i][j]; if (c == "#" || p.next[c - "a"] == null) return; p = p.next[c - "a"]; if (p.word != null) { result.add(p.word); p.word = null; //去重 } board[i][j] = "#"; int[][] dir = {{-1, 0}, {1, 0}, {0, -1}, {0, 1}}; for (int k = 0; k < dir.length; k++) { int x = i + dir[k][0], y = j + dir[k][1]; if (x < 0 || x > board.length - 1 || y < 0 || y > board[i].length - 1) continue; dfs(result, board, p, x, y); } board[i][j] = c; } public List findWords(char[][] board, String[] words) { List result = new ArrayList (); if (board == null || board.length == 0 || board[0].length == 0) return result; TrieNode root = buildTrie(words); for (int i = 0; i < board.length; i++) { for (int j = 0; j < board[i].length; j++) { dfs(result, board, root, i, j); } } return result; }
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://m.specialneedsforspecialkids.com/yun/64976.html
Problem Given a 2D board and a list of words from the dictionary, find all words in the board. Each word must be constructed from letters of sequentially adjacent cell, where adjacent cells are those ...
摘要:練級攻略的縱向編輯模式第一步修改將數列中第二段所有數字修改為將游標定位第一個行的進入縱向編輯模式移動游標到最后一行,可視塊覆蓋所要修改的列進入修改模式輸入數字第二步前添加在所有行之前添加將游標定位到第一行第一列進入縱向編輯模式 vimtutor showImg(https://segmentfault.com/img/bV4OLS?w=600&h=400); intro vim hi...
摘要:子域授權比如我的一臺服務器負責的權威域名解析,它再授權服務器對的子域名進行解析,這就叫做子域授權。之后,通過自己的會話密鑰將要發送的明文進行加密,發送給,通過事先得到的會話密鑰對發送過來的密文進行解密從而得到明文。 還是出于項目的需要,把Bind比較高級的功能做一個梳理,這其中包含:DNS遞歸迭代查詢、DNS子域授權、DNS轉發、DNS主從區域傳輸、DNS數據加密,每一個內容不僅記錄了...
閱讀 2383·2021-11-24 10:26
閱讀 2583·2021-11-16 11:44
閱讀 1701·2021-09-22 15:26
閱讀 3577·2021-09-10 11:11
閱讀 3190·2021-09-07 10:25
閱讀 3627·2021-09-01 10:41
閱讀 1012·2021-08-27 13:11
閱讀 3509·2021-08-16 11:02