每天学一个算法--倒排索引(Inverted Index)

📘 教案 25:倒排索引(Inverted Index · 工程级)


一、问题模型

设有文档集合:

D=d1,d2,...,dn\]\[ D = {d_1, d_2, \\dots, d_n} \]\[D=d1,d2,...,dn

每个文档由一系列词组成。

给定查询词 ( q ),需要快速找到:

di∣q∈di\]\[ { d_i \\mid q \\in d_i } \]\[di∣q∈di


二、朴素方法及其问题


方法:逐文档扫描

对每个文档判断是否包含词 (q)


复杂度

O(∣D∣⋅L)\]\[ O(\|D\| \\cdot L) \]\[O(∣D∣⋅L)

其中 (L) 为文档平均长度。


问题

  • 无法扩展到大规模数据
  • 查询延迟高

三、倒排索引的定义


倒排索引是从"词 → 文档列表"的映射结构


正排索引(Forward Index)

text 复制代码
doc1 → [word1, word2, ...]

倒排索引(Inverted Index)

text 复制代码
word1 → [doc1, doc3, doc7]
word2 → [doc2, doc3]

👉 查询时直接定位相关文档集合


四、核心结构


1. 词典(Dictionary)

存储:

term→posting list\]\[ term \\rightarrow posting\\ list \]\[term→posting list


2. 倒排列表(Posting List)

对于每个词:

text 复制代码
word → [docID1, docID2, ...]

扩展信息(实际系统)

text 复制代码
word → [(docID, tf, positions...)]

五、构建过程(关键)


Step 1:分词(Tokenization)

将文档拆分为词项


Step 2:归一化

  • 小写化
  • 去停用词
  • 词干提取

Step 3:构建映射

text 复制代码
term → docID

Step 4:排序

每个 posting list 按 docID 排序


六、查询处理


1. 单词查询

直接返回 posting list


2. 多词查询(AND)

例如:

text 复制代码
q = "apple AND banana"

执行:

posting list 的交集


算法(双指针)

text 复制代码
A: [1,3,5,8]
B: [3,5,7]

过程:

  • 比较 A[i] 和 B[j]
  • 相等 → 加入结果
  • 小的指针前进

复杂度

O(∣A∣+∣B∣)\]\[ O(\|A\| + \|B\|) \]\[O(∣A∣+∣B∣)


七、优化:跳跃表(Skip Pointers)


在 posting list 中增加跳跃指针:

text 复制代码
1 → 5 → 9 → ...

👉 快速跳过不可能匹配的区间


八、排名(Ranking)


查询不仅要"找到",还要"排序"。


TF-IDF


定义:

TF=词频\]\[ TF = \\text{词频} \]\[TF=词频

IDF=log⁡Ndf\]\[ IDF = \\log \\frac{N}{df} \]\[IDF=logdfN


得分:

score(d,q)=TF⋅IDF\]\[ score(d, q) = TF \\cdot IDF \]\[score(d,q)=TF⋅IDF



含义

  • 出现频率高 → 更重要
  • 出现在少数文档 → 更有区分度

九、工程结构(关键)


1️⃣ 倒排索引存储

  • 磁盘文件(通常压缩)
  • 按 term 排序

2️⃣ 构建过程

👉 使用外部排序:

  • term → docID
  • 排序
  • 合并

3️⃣ 更新问题


不能直接修改:

👉 采用 LSM-Tree 思想:

  • 新数据 → 新索引段
  • 后台合并

十、压缩(非常重要)


posting list 通常很大:


方法

  • 差分编码(Delta Encoding)
  • 变长编码(Varint)

👉 减少存储与 I/O


十一、系统整体结构


text 复制代码
用户查询
   ↓
解析(分词)
   ↓
查倒排索引
   ↓
合并 posting list
   ↓
计算得分(TF-IDF)
   ↓
返回 Top-K

十二、与前面内容的关系


模块 对应算法
构建索引 外部排序
存储 LSM-Tree
查询 双指针 / 二分
加速 Bloom Filter

👉 这是完整链路


十三、本质总结(严肃表达)


倒排索引通过建立词项到文档集合的映射,将原本需要扫描全文的查询问题转化为集合运算问题,从而在大规模文本检索中实现高效查询。

相关推荐
小e说说1 小时前
打破偏科困境:这些学习软件助孩子重燃学习热情
算法
月昤昽2 小时前
autoCAD二次开发 4.正多边形与collection区分
算法·c#·二次开发·autocad二次开发
休息一下接着来2 小时前
C++ 固定容量环形队列实现
c++·算法
im_AMBER3 小时前
手撕hot100之矩阵!看完这篇就AC~
javascript·数据结构·线性代数·算法·leetcode·矩阵
笨笨饿3 小时前
#79_NOP()嵌入式C语言中内联汇编宏的抽象封装模式研究
linux·c语言·网络·驱动开发·算法·硬件工程·个人开发
风萧萧19993 小时前
问答样例如何在RAG问答中使用?
算法
七夜zippoe4 小时前
DolphinDB分区策略:HASH分区与COMPO分区
算法·哈希算法·hash·dolphindb·compo
沪漂阿龙4 小时前
程序员面试技术爆款文:2026大厂算法通关手册——从零基础到LeetCode刷穿,这一篇就够了
算法·leetcode·面试
rit84324995 小时前
基于博弈论的小区分簇算法MATLAB实现
开发语言·算法·matlab