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.

Example:

Input:
board = [
['o','a','a','n'],
['e','t','a','e'],
['i','h','k','r'],
['i','f','l','v']
]
words = ["oath","pea","eat","rain"] Output: ["eat","oath"]

Note:

  1. All inputs are consist of lowercase letters a-z.
  2. The values of words are distinct.

You would need to optimize your backtracking to pass the larger test. Could you stop backtracking earlier?

If the current candidate does not exist in all words' prefix, you could stop backtracking immediately. What kind of data structure could answer such query efficiently? Does a hash table work? Why or why not? How about a Trie? If you would like to learn how to implement a basic trie, please work on this problem: Implement Trie (Prefix Tree) first.

这道题是在之前那道 Word Search 的基础上做了些拓展,之前是给一个单词让判断是否存在,现在是给了一堆单词,让返回所有存在的单词,在这道题最开始更新的几个小时内,用 brute force 是可以通过 OJ 的,就是在之前那题的基础上多加一个 for 循环而已,但是后来出题者其实是想考察字典树的应用,所以加了一个超大的 test case,以至于 brute force 无法通过,强制我们必须要用字典树来求解。LeetCode 中有关字典树的题还有 Implement Trie (Prefix Tree) 和 Add and Search Word - Data structure design,那么我们在这题中只要实现字典树中的 insert 功能就行了,查找单词和前缀就没有必要了,然后 DFS 的思路跟之前那道 Word Search 基本相同,请参见代码如下:

class Solution {
public:
struct TrieNode {
TrieNode *child[];
string str;
TrieNode() : str("") {
for (auto &a : child) a = NULL;
}
};
struct Trie {
TrieNode *root;
Trie() : root(new TrieNode()) {}
void insert(string s) {
TrieNode *p = root;
for (auto &a : s) {
int i = a - 'a';
if (!p->child[i]) p->child[i] = new TrieNode();
p = p->child[i];
}
p->str = s;
}
};
vector<string> findWords(vector<vector<char>>& board, vector<string>& words) {
vector<string> res;
if (words.empty() || board.empty() || board[].empty()) return res;
vector<vector<bool>> visit(board.size(), vector<bool>(board[].size(), false));
Trie T;
for (auto &a : words) T.insert(a);
for (int i = ; i < board.size(); ++i) {
for (int j = ; j < board[i].size(); ++j) {
if (T.root->child[board[i][j] - 'a']) {
search(board, T.root->child[board[i][j] - 'a'], i, j, visit, res);
}
}
}
return res;
}
void search(vector<vector<char>>& board, TrieNode* p, int i, int j, vector<vector<bool>>& visit, vector<string>& res) {
if (!p->str.empty()) {
res.push_back(p->str);
p->str.clear();
}
int d[][] = {{-, }, {, }, {, -}, {, }};
visit[i][j] = true;
for (auto &a : d) {
int nx = a[] + i, ny = a[] + j;
if (nx >= && nx < board.size() && ny >= && ny < board[].size() && !visit[nx][ny] && p->child[board[nx][ny] - 'a']) {
search(board, p->child[board[nx][ny] - 'a'], nx, ny, visit, res);
}
}
visit[i][j] = false;
}
};

Github 同步地址:

https://github.com/grandyang/leetcode/issues/212

类似题目:

Word Search

Unique Paths III

参考资料:

https://leetcode.com/problems/word-search-ii/

https://leetcode.com/problems/word-search-ii/discuss/59780/Java-15ms-Easiest-Solution-(100.00)

https://leetcode.com/problems/word-search-ii/discuss/59784/My-simple-and-clean-Java-code-using-DFS-and-Trie

LeetCode All in One 题目讲解汇总(持续更新中...)

[LeetCode] Word Search II 词语搜索之二的更多相关文章

  1. [LeetCode] 212. Word Search II 词语搜索之二

    Given a 2D board and a list of words from the dictionary, find all words in the board. Each word mus ...

  2. [LeetCode] 212. Word Search II 词语搜索 II

    Given a 2D board and a list of words from the dictionary, find all words in the board. Each word mus ...

  3. [LeetCode] Word Pattern II 词语模式之二

    Given a pattern and a string str, find if str follows the same pattern. Here follow means a full mat ...

  4. [LeetCode] Word Ladder II 词语阶梯之二

    Given two words (start and end), and a dictionary, find all shortest transformation sequence(s) from ...

  5. [LeetCode] 126. Word Ladder II 词语阶梯之二

    Given two words (beginWord and endWord), and a dictionary's word list, find all shortest transformat ...

  6. [LeetCode] Word Break II 拆分词句之二

    Given a string s and a dictionary of words dict, add spaces in s to construct a sentence where each ...

  7. LeetCode() Word Search II

    超时,用了tire也不行,需要再改. class Solution { class TrieNode { public: // Initialize your data structure here. ...

  8. Leetcode之回溯法专题-212. 单词搜索 II(Word Search II)

    Leetcode之回溯法专题-212. 单词搜索 II(Word Search II) 给定一个二维网格 board 和一个字典中的单词列表 words,找出所有同时在二维网格和字典中出现的单词. 单 ...

  9. [LeetCode] Word Search 词语搜索

    Given a 2D board and a word, find if the word exists in the grid. The word can be constructed from l ...

随机推荐

  1. 5分钟创建一个SpringBoot + Themeleaf的HelloWord应用

    第一步:用IDE创建一个普通maven工程,我用的eclipse. 第二步:修改pom.xml,加入支持SpringBoot和Themeleaf的依赖,文件内容如下: <?xml version ...

  2. 使用Eclipse创建Maven Web工程

    方法/步骤 1 使用Eclipse创建Maven Web工程 2 找到Maven Project,点击Next 3 勾选上Create a simple project (不使用骨架),Next 4 ...

  3. Java多线程--让主线程等待子线程执行完毕

    使用Java多线程编程时经常遇到主线程需要等待子线程执行完成以后才能继续执行,那么接下来介绍一种简单的方式使主线程等待. java.util.concurrent.CountDownLatch 使用c ...

  4. Python 生成器与迭代器 yield 案例分析

    前几天刚开始看 Python ,后因为项目突然到来,导致Python的学习搁置了几天.然后今天看回Python 发现 Yield 这个忽然想不起是干嘛用的了(所以,好记性不如烂笔头.).然后只能 花点 ...

  5. app端上传文件至服务器后台,web端上传文件存储到服务器

    1.android前端发送服务器请求 在spring-mvc.xml 将过滤屏蔽(如果不屏蔽 ,文件流为空) <!-- <bean id="multipartResolver&q ...

  6. 移动端web开发——视口

    本篇主要是记录一下移动端视口的分类说明和其它的一些知识.在开始之前,先看一个典型的例子: <meta name="viewport" content="width= ...

  7. 我的屌丝giser成长记-研三篇

    进入研三以来,基本都是自己的自由时间了,从导师的项目抽离出来,慢慢的都交给师弟他们来负责.研三的核心任务就是找工作以及写毕业论文,因为有导师科研基金项目成果作为支撑,所以自己的论文没什么可担心,一切都 ...

  8. Using View and Data API with Meteor

    By Daniel Du I have been studying Meteor these days, and find that Meteor is really a mind-blowing f ...

  9. DataView详解

    dataview可以用于对你的datatable筛选,搜索,排序,编辑和导航.可以方便对databale的操作. 先来看一下它有哪些属性: 接下来是方法: 我们怎么使用它呢? public datat ...

  10. 整理常用加密 iOS 与 Android 加密 MD5-SHA1

    1.MD5算法 不可逆 128位或者64位串,byte数字长度就是16和8,一般表示是使用16进制来表示的话,1个byte转换成2个16bit,分别表示高地位,所以生成的字符串是16位或者是32位的, ...