字典树
字典树(Trie)¶
简介¶
字典树(Trie,前缀树)可用于维护字符串集合。还可以维护前缀等信息。
代码¶
所需头文件:
<array><vector><string_view>
struct trie {
struct node {
std::array<int, 26> next;
int cnt = 0;
node() {
next.fill(-1);
}
};
std::vector<node> tree;
trie() {
tree.emplace_back();
}
void insert(std::string_view sv) {
int p = 0;
for (auto c : sv) {
int idx = c - 'a';
if (tree[p].next[idx] == -1) {
tree[p].next[idx] = static_cast<int>(tree.size());
tree.emplace_back();
}
p = tree[p].next[idx];
}
++tree[p].cnt;
}
int query(std::string_view sv) const {
int p = 0;
for (auto c : sv) {
int idx = c - 'a';
if (tree[p].next[idx] == -1) {
return 0;
}
p = tree[p].next[idx];
}
return tree[p].cnt;
}
};
复杂度¶
设字符集大小为 \(\sigma\),本实现中 \(\sigma=26\)。
设 \(L\) 为当前 insert 或 query 的字符串长度,\(N\) 为 Trie 中节点总数(含根),\(m\) 为所有插入字符串的总长度,\(M\) 为所有查询字符串的总长度。
| 项目 | 复杂度 |
|---|---|
初始化 trie() |
\(\Theta(\sigma)\) |
| 新建一个节点(均摊) | \(\Theta(\sigma)\) |
insert(sv) 单次最坏 |
\(\Theta(L\sigma)\) |
query(sv) 单次最坏 |
\(\Theta(L)\) |
| 插入总长度 \(m\)、总节点数 \(N\) | \(O(m + N\sigma)\) |
| 查询总长度 \(M\) | \(O(M)\) |
| 结构自身占用空间 | \(\Theta(N\sigma)\) |