字典
实现字典可以采取以下的数据结构,他们个有优缺点
- 排序列表Array/List 使用二分法查找,不平衡
- HashMap/TreeMap 性能高,内存消耗大,几乎是原始数据的三倍
- Skip List 跳跃表,可快速查找词语,在lucene、redis、Hbase等均有实现。相对于TreeMap等结构,特别适合高并发场景(Skip List介绍)
- Trie 适合英文词典,如果系统中存在大量字符串且这些字符串基本没有公共前缀,则相应的trie树将非常消耗内存(数据结构之trie树)
- Double Array Trie 适合做中文词典,内存占用小,很多分词工具均采用此种算法(深入双数组Trie)
- Ternary Search Tree 三叉树,每一个node有3个节点,兼具省空间和查询快的优点(Ternary Search Tree)
- Finite State Transducers (FST) 一种有限状态转移机,Lucene 4有开源实现,并大量使用
mop/0(/为被索引项目)
moth/1
pop/2
star/3
stop/4
top/5
zzz/10
的构建结果是
通过FST,可以快速判断一个字符是否存在,并可以快速找到索引项。同时能充分利用前缀和后缀,节省存储空间。
Lucene
luncense的目的是建立一个全文检索的工具包。
显然上面针对一个个字母建立fst是不靠谱的(保存指针的空间你足够保存好几个字符了)。所以,上述的每一个字母在实际应用中是代表一个“词“。这就需要分词器。Lucene支持多种分词器。通过分词器,可以查找文件的若干词。
如果说一般的索引是指,“文章号”对“文章中所有关键词”。
那么倒排索引把这个关系倒过来,变成:“关键词”对“拥有该关键词的所有文章号”。所谓倒排索引,一般是通过FST和SkipLIst实现的。