单词搜索 II · Word Search II
[抄题]:
给出一个由小写字母组成的矩阵和一个字典。找出所有同时在字典和矩阵中出现的单词。一个单词可以从矩阵中的任意位置开始,可以向左/右/上/下四个相邻方向移动。
给出矩阵:
doaf
agai
dcan
和字典:
{"dog", "dad", "dgdg", "can", "again"}
[暴力解法]:
时间分析:
空间分析:
[思维问题]:
- 用p指针进行比较,不知道指针应该怎么用,指针就是一个新类,利用其中的TrieNode[] next数组移动即可。表示节点的初始化,
p = p.next[c - 'a'];使节点等于初始化之后的值。
- 为防止出现res中有相同单词,每添加一个单词后就设其为空, 不同路线相同结果时要想到
[一句话思路]:
[输入量]:空: 正常情况:特大:特小:程序里处理到的特殊情况:异常情况(不合法不合理的输入):
[画图]:
在trie的结构中,字母其实是线段和下一个节点共有的,所以trienode中的节点数组命名为next
建树时,每个单词都用p从root开始重新新建
[一刷]:
- dfs的参数在总函数中有用的变量一一对应就行了,数组名还是要有的
- next[],忘记了 数组括号中一定只能是数字,不能是别的,应该是c - 'a'
- board[i][j]直接= 字母c就行了,不用加‘’
- 纠结不清的:dfs的表达式上限是由总表达式的上限决定的,
i < board.length, dfs(i+1)也要带入后符合规则,故
i < board.length - 1
[二刷]:
- 当前字母对应的节点p.next[c - 'a'];非空时,说明trie中已经存了和图中相对应的节点,p就应该指向当前对应的字母节点,否则新建。没有理解
- w循环时,其对应的每个单词都要加入到p.word中,没有条件,不理解
[三刷]:
[四刷]:
[五刷]:
[五分钟肉眼debug的结果]:
[总结]:
- 当前字母对应的节点p.next[c - 'a'];非空时,说明trie中已经存了和图中相对应的节点,p就应该指向当前对应的字母节点,否则新建。没有理解
[复杂度]:Time complexity: O(4*深度次方,最大m+n) Space complexity: O(<n)
[英文数据结构或算法,为什么不用别的数据结构或算法]:
- 新建的一棵trie树,按道理应该习惯命名为root
- 可以有几个类,但是只能有一个public的类 其他的你就只能定义class而已
- 当 java 一个 class 里面 包含 另一个 class 时,需要将这个子 class 声明为 static,不然经常出错
[关键模板化代码]:
for (String w : words){
TrieNode p = root;
//add a c
for (char c : w.toCharArray()) {
int i = c - 'a';
if (p.next[i] == null) {
p.next[i] = new TrieNode();
}
//asign!
p = p.next[i];
}
//add word
p.word = w;//only mean to w, sure to have word
}
指针开始指向root,之后指向别的
[其他解法]:
[Follow Up]:
[LC给出的题目变变变]:
word search1 : dfs
[代码风格] :
j的for循环写成i了,查了半小时,后悔死。好像老是出现这个错误吧?要避免。
class Solution {
//class
class TrieNode {
TrieNode[] next = new TrieNode[26];
String word;
} public List<String> findWords(char[][] board, String[] words) {
List<String> res = new ArrayList<String>();
TrieNode root = buildTrie(words); for (int i = 0; i < board.length; i++) {
for (int j = 0; i < board[0].length; j++) {
dfs(board, i, j, root, res);
}
}
return res;
}
//dfs
public void dfs(char[][] board, int i, int j, TrieNode p, List<String> res) {
//exit
//no c or no node
char c = board[i][j];
if (c == '#' || p.next[c - 'a'] == null) {//exit in dfs
return ;
}
//asign
p = p.next[c - 'a'];
//add word
if (p.word != null) {
res.add(p.word);
p.word = null;
}
//dfs
board[i][j] = '#';
if (i < board.length - 1) dfs(board, i + 1, j, p, res);
if (j < board[0].length - 1) dfs(board, i, j + 1, p, res);
if (i > 0) dfs(board, i - 1, j, p, res);
if (j > 0) dfs(board, i, j - 1, p, res);
board[i][j] = c;
}
//buildTrie
public TrieNode buildTrie (String[] words) {
//build a root
TrieNode root = new TrieNode();
//add all words's node
for (String w : words){
TrieNode p = root;
//add a c
for (char c : w.toCharArray()) {
int i = c - 'a';
if (p.next[i] == null) {
p.next[i] = new TrieNode();
}
}
//add word
if (p.word != null) {
res.add(p.word);
}
}
return root;
}
}
单词搜索 II · Word Search II的更多相关文章
- Leetcode之回溯法专题-79. 单词搜索(Word Search)
Leetcode之回溯法专题-79. 单词搜索(Word Search) 给定一个二维网格和一个单词,找出该单词是否存在于网格中. 单词必须按照字母顺序,通过相邻的单元格内的字母构成,其中“相邻”单元 ...
- [Swift]LeetCode212. 单词搜索 II | Word Search II
Given a 2D board and a list of words from the dictionary, find all words in the board. Each word mus ...
- LeetCode 79. 单词搜索(Word Search)
题目描述 给定一个二维网格和一个单词,找出该单词是否存在于网格中. 单词必须按照字母顺序,通过相邻的单元格内的字母构成,其中“相邻”单元格是那些水平相邻或垂直相邻的单元格.同一个单元格内的字母不允许被 ...
- Leetcode之回溯法专题-212. 单词搜索 II(Word Search II)
Leetcode之回溯法专题-212. 单词搜索 II(Word Search II) 给定一个二维网格 board 和一个字典中的单词列表 words,找出所有同时在二维网格和字典中出现的单词. 单 ...
- leetcode 79. Word Search 、212. Word Search II
https://www.cnblogs.com/grandyang/p/4332313.html 在一个矩阵中能不能找到string的一条路径 这个题使用的是dfs.但这个题与number of is ...
- [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 ...
- [LeetCode] Word Search II 词语搜索之二
Given a 2D board and a list of words from the dictionary, find all words in the board. Each word mus ...
- [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 ...
- 【leetcode】212. Word Search II
Given an m x n board of characters and a list of strings words, return all words on the board. Each ...
随机推荐
- C#读写三菱Fx PLC 使用Fx 串口协议 读写Fx3U设备
本文将使用一个Github开源的组件库技术来读写三菱 FX PLC,使用的是基于串口的实现,不需要额外的组件,读取操作只要放到后台线程就不会卡死线程,本组件支持超级方便的高性能读写操作 github地 ...
- linux磁盘分区格式化-fdisk命令工具
本文主要讲述使用fdisk工具对磁盘进行分区和格式化的方法 首先要明确分区是针对磁盘进行的操做,磁盘分区会创建分区表,类似vda,sda的是磁盘,vda1,sda1的是分区 1.查看磁盘分区状态 1. ...
- B树、B-树、B+树、B*树都是什么
B树.B-树.B+树.B*树都是什么 B树 即二叉搜索树: 1.所有非叶子结点至多拥有两个儿子(Left和Right): 2.所有结点存储一个关键字: 3.非叶子结点的左指针指向小于其关键字的子树,右 ...
- Codeforces 148B: Escape
题目链接:http://codeforces.com/problemset/problem/148/B 题意:公主从龙的洞穴中逃跑,公主的速度为vp,龙的速度为vd,在公主逃跑时间t时,龙发现公主逃跑 ...
- SpookyOTP
https://pypi.python.org/pypi/SpookyOTP/1.1.1 SpookyOTP 1.1.1 Downloads ↓ A lightweight Python 2/3 pa ...
- 修改panabit web管理介面端口
panabit使用mini_httpd为web发布平台,版本为1.19.使用https协议发布,端口443,运行命令为/usr/panabit/bin/ipe_httpd. panabit启动时使用/ ...
- 智能家居入门DIY——【五、执行命令】
前面几篇介绍了ESP8266使用AT命令来连接WIFI实现一系列功能.这一篇介绍一下使用Wemos D1 Wifi来进行开发,当然也可以用常见的8针ESP8266来完成(只是需要按网上的方法将Ardu ...
- [转]JavaScript RegExp 对象参考手册
JavaScript RegExp 对象参考手册 RegExp 对象 RegExp 对象表示正则表达式,它是对字符串执行模式匹配的强大工具. 直接量语法 /pattern/attributes 创建 ...
- 寒武纪-1005 Travel(树形DP)
一.题目链接 http://aiiage.hustoj.com/problem.php?id=1005 二.题面 PDF:http://aiiage.hustoj.com/upload/file/20 ...
- 软件测试——Peer Review
一.什么是peer review peer review是一种通过作者的同行来确认缺陷和需要变更区域的检查方法.需要进行同行评审的特定产品在定义项目软件过程的时候被确定并且作为软件开发计划的一部分被安 ...