四、字典树 Trie 单词查找树 前缀树
解决字符串类型的问题:1.单词查找
2.字符串排序
构建复杂度:O(NxM)
查找复杂度:O(M)
优点:查找高效、利用了前缀节省空间
缺点:空间复杂度高
适用场景:通常前缀重合多才好用
对指针存数据不友好,对CPU缓存不友好
适合前缀查找、自动补全
单纯查找字符串是否存在,用hash表反而更好
编程技巧: 用数组实现树
扩展: 双数组字典树
优化字典树存储稀疏的问题
base数组:解决如何冲突?
check数组:亲子鉴定 保存父指针 正负号确定独立成词
应用: 离线构造,在线查询
缺点:构造时间非常长、使用场景固定
扩展2: 马拉车算法 O(N)
解决回文串处理问题:1、暴力
2、二分+hash
3、马拉车算法,回文子串
4、回文自动机
五、字符串匹配算法
1、朴素匹配算法 BF算法 O(NxM)
2、hash匹配算法 RK算法 O(N) 最坏O(NxM)
计算子串O(N)
对比O(n - m + 1)
3、KMP算法 O(N+M)
缓存信息
next数组
4、Sunday算法 O(N) 最坏O(NxM)
简单
5、SHIFT-AND算法 O(N)
转换 + 二进制
六、AC自动机
在Trie中加入失败指针,通过路径压缩优化
找S中包含哪些给定子串
匹配的时间复杂度O(N) 最坏O(高度 x 词数)
七、哈夫曼编码
贪心算法
借助堆创建哈夫曼树
哈夫曼编码是最优的变长编码
扩展3: LRU缓存机制
最近最少机制
实现:链表存储 + hash表查询
八、图论
最小生成树算法
从带权图中抽出一颗生成树,使得边的权值最小
1. kruscal算法 O(ElogE) E:边数
1.sort边 2、遍历边 3. 边的两个点加入T
2. Prim算法 O(V^2) V:定点数
最短路问题
求一个起点到其余各个顶点的最短路径
Dijkstra算法 O(V^2 + E)
{S = 点集} {T = 空集}
(1)每次从S中找一个最近点放入T中
(2)然后进行松弛操作,更新距离
(3)直到S为空