大家好,我是小魔龙,Unity3D软件工程师,VR、AR,虚拟仿真方向,不定时更新软件开发技巧,生活感悟,觉得有用记得一键三连哦。
“实现Trie类,Trie类是一种树形数据结构,用于高效储存和检索字符串数据集中的键。”
题目链接:
来源:力扣(LeetCode)
链接: 208. 实现 Trie (前缀树) - 力扣(LeetCode)
Trie(发音类似 "try")或者说 前缀树 是一种树形数据结构,用于高效地存储和检索字符串数据集中的键。这一数据结构有相当多的应用情景,例如自动补完和拼写检查。
请你实现 Trie 类:
示例 1:
输入
["Trie", "insert", "search", "search", "startsWith", "insert", "search"]
[[], ["apple"], ["apple"], ["app"], ["app"], ["app"], ["app"]]
输出
[null, null, true, false, true, null, true]
解释
Trie trie = new Trie();
trie.insert("apple");
trie.search("apple"); // 返回 True
trie.search("app"); // 返回 False
trie.startsWith("app"); // 返回 True
trie.insert("app");
trie.search("app"); // 返回 True
示例 2:
题意要求实现一个Trie 类,也就是前缀树,前缀树是一种树形数据结构,用于高效地存储和检索字符串数据集中的键。
Trie是一颗非典型的多叉树模型,也就是每个节点的分支数量可能为多个。
之所以说是非典型的树,是因为它跟一般的多叉树不一样,一般的多叉树的节点是有一个节点值,还有一个指向子节点的指针。
而Trie的节点有一个标记值,标记该节点是否是一个串的结束,还有一个字母映射表。
Trie为什么要这么设计呢,Trie的节点值并没有直接保存字符值的数据,而是用了一个字母映射表,字母映射表中保存了对当前节点而言下一个可能出现的所有字符的链接,比如下面三个单词"sea","sells","she"在Trie的样子:
Trie中一般含有大量的空链接,因此在绘制一颗前缀树通常忽略空链接,也就是这样:
接下来就来实现对Trie的一些常用操作方法吧。
首先是插入字符串,有两种情况:
重复以上步骤,直到处理字符串的最后一个字符,将当前节点标记为字符串的结尾。
查找前缀,也有两种情况:
重复以上步骤,直到返回空指针或搜索完前缀的最后一个字符。
代码参考:
class Trie {
private Trie[] children;
private boolean isEnd;
public Trie() {
children = new Trie[26];
isEnd = false;
}
public void insert(String word) {
Trie node = this;
for (int i = 0; i < word.length(); i++) {
char ch = word.charAt(i);
int index = ch - 'a';
if (node.children[index] == null) {
node.children[index] = new Trie();
}
node = node.children[index];
}
node.isEnd = true;
}
public boolean search(String word) {
Trie node = searchPrefix(word);
return node != null && node.isEnd;
}
public boolean startsWith(String prefix) {
return searchPrefix(prefix) != null;
}
private Trie searchPrefix(String prefix) {
Trie node = this;
for (int i = 0; i < prefix.length(); i++) {
char ch = prefix.charAt(i);
int index = ch - 'a';
if (node.children[index] == null) {
return null;
}
node = node.children[index];
}
return node;
}
}
时间复杂度:O(1)
时间复杂度初始为O(1),其余操作为O(|S|),其中|S|是每次插入或查询字符串的长度。
空间复杂度:O(|T|·∑)
其中|T|是所有插入字符串的长度和,∑为字符集的大小。
通过以上介绍和代码实现我们可以总结出 Trie 的几点性质:
最后,关于 Trie 的应用场景,希望你能记住 8 个字:一次建树,多次查询。