BM25算法与文本排序
BM25 根据词项匹配和语料统计为候选文本排序。
BM25 是全文检索中的相关性评分算法。 给定查询,它依据查询词在候选文本中的出现次数、词在整批文本中的常见程度,以及文本长度计算分数。分数决定候选文本的排序。
候选文本可以是一句话、一段话或整篇文章。BM25 按分词后的词项评分,不直接计算两句话的语义相似度。
1. 词项匹配与相关性评分
查询和候选文本经过分词等处理,得到用于检索的词项。倒排索引按查询词项找出候选文档;BM25 根据词频和整批文档的统计量打分。
匹配条件决定候选范围。 要求命中任意词项时,只命中一个词项的文档也能参与排序;要求全部命中时,它就不在候选结果中。
2. BM25 评分公式
公式针对单个检索字段,重复的查询词项只计一次:
- :词项 在文档 中的出现次数;没有出现时,该词项贡献为零。
- 与 :文档总数,以及包含 的文档数。
- 与 :文档的词项数,以及语料中的平均文档长度。这些统计量应来自同一检索字段和同一批文档。
- 与 :分别控制重复词的收益递减速度、文档长度对评分的影响。
一个词在同一篇文档里出现三次,文档频率仍只增加一。
IDF 使用 Lucene 的非负写法。词频项省略了另一种写法中的 ;对同一查询和字段,这个系数只会等比例改变分数,不改变排名。
2.1 常见词的贡献较小
在同一批文档中,包含某词项的文档越多,它的 IDF 越低。 IDF 反映词项在这批文档里的常见程度,不能据此判断它的语义重要性。
2.2 重复词的收益递减
固定文档长度和 后,词频部分的形式是 ,其中 。词频继续增加,得分仍会上升,但每增加一次带来的收益变小。
例如 且文档长度等于平均长度时,。词频为 时,该项是 ;词频为 时是 ,没有变成三倍。 越大,收益下降得越慢。
2.3 文档长度改变词频的作用
当 ,查询词出现次数相同的两篇文档中,较长文档的分母更大,单个词项的贡献较低。 若较长文档同时多次命中查询词,总分仍可能更高。 时不做长度调整; 时使用完整的长度比例。
3. 四条商品描述的排序
查询“防水背包”拆成“防水”“背包”两个词项。四条商品描述分别作为文档 D1~D4。至少命中一个查询词项即可参与排序,取 、。词项由人工指定,标点不计入长度,不代表某个中文分词器的输出。
- D1:“防水背包适合通勤。” →
防水 / 背包 / 适合 / 通勤(4 个词项)- D2:“这款防水背包采用防水面料,配有防水拉链,适合雨天通勤。” →
这款 / 防水 / 背包 / 采用 / 防水 / 面料 / 配有 / 防水 / 拉链 / 适合 / 雨天 / 通勤(12 个词项)- D3:“轻便的防水背包有多个收纳隔层,适合周末出行。” →
轻便 / 的 / 防水 / 背包 / 有 / 多个 / 收纳 / 隔层 / 适合 / 周末 / 出行(11 个词项)- D4:“这款背包适合日常通勤,设有电脑隔层。” →
这款 / 背包 / 适合 / 日常 / 通勤 / 设有 / 电脑 / 隔层(8 个词项)
平均文档长度为 ;“防水”出现在三条描述中,IDF 约为 ;“背包”四条都有,IDF 约为 。
D1 的长度调整项为 。两个查询词各出现一次,所以分数为 。其余文档按同一公式计算:
| 排名 | 文档 | BM25 分数 |
|---|---|---|
| 1 | D2 | 0.303841 |
| 2 | D1 | 0.267293 |
| 3 | D3 | 0.217064 |
| 4 | D4 | 0.053834 |
D1 与 D3 的两个查询词都只出现一次;D3 更长,分数较低。D2 的“防水”出现三次,词频带来的增益超过长度的影响。 D4 只命中较常见的“背包”,排在最后。
4. Python 实现
脚本只用 Python 标准库。BM25 接收人工指定的词项列表,不包含中文分词器;原句只用于展示排序结果。
rank()遍历所有文档,只返回正分结果,按分数降序排列;同分时保持输入顺序。
| |
| |
这份实现逐篇计算分数,没有建立倒排索引。搜索系统的分词结果、字段权重或 BM25 参数不同,分数就可能与表中不同。
BM25 分数在同一查询、语料和评分设置下用于排序,不能当作相关概率。
5. BM25 与TF-IDF 区别
TF-IDF 有对数词频、长度归一化等变体。这里比较词频取出现次数、IDF 取 ,且不做长度归一化的写法。
| 比较项 | TF-IDF | BM25 |
|---|---|---|
| 词频 | 同一词项每多出现一次,分数增加相同的量。 | 分数仍上升,但增量逐渐减小。 |
| 文档长度 | 不调整文档长度。 | 用 控制长度对词频贡献的影响。 |
| IDF | 文档频率越高,IDF 越低;词项出现在所有文档中时为零。 | 文档频率越高,IDF 越低;词项出现在所有文档中时仍为正。 |
评论
使用 GitHub 登录后参与讨论,评论将公开保存在 GitHub。
站长管理删除会同步到 GitHub,无法撤销。
阅读到这里时加载评论。