【问题标题】:Lucene fieldNorm discrepancy between Similarity calculation and query-time value相似度计算和查询时间值之间的 Lucene fieldNorm 差异
【发布时间】:2013-02-14 15:55:55
【问题描述】:

我试图了解fieldNorm 是如何计算的(在索引时),然后在查询时使用(并且显然是重新计算)。

在所有示例中,我使用的是没有停用词的 StandardAnalyzer。

在索引内容时调试 DefaultSimilaritycomputeNorm 方法,我注意到它返回了 2 个特定文档:

  • 文档 A 为 0.5(其字段中有 4 个标记)
  • 0.70710677 用于文档 B(其字段中有 2 个标记)

它通过使用公式来做到这一点:

state.getBoost() * ((float) (1.0 / Math.sqrt(numTerms)));

boost 始终为 1

之后,当我查询这些文档时,我看到在查询说明中我得到了

  • 0.5 = fieldNorm(field=titre, doc=0) 用于文档 A
  • 0.625 = fieldNorm(field=titre, doc=1) 用于文档 B

这已经很奇怪了(对我来说,我确定是我错过了一些东西)。为什么我得到的字段规范值与索引时计算的值不同?这是正在实施的“查询规范化”吗?如果是这样,它是如何工作的?

但这或多或少是可以的,因为两个查询时 fieldNorm 的顺序与索引时计算的顺序相同(在这两种情况下,值较短的字段具有较高的 fieldNorm)

然后我创建了自己的 Similarity 类,在其中实现了 computeNorms 方法,如下所示:

public float computeNorm(String pField, FieldInvertState state) {
    norm = (float) (state.getBoost() + (1.0d / Math.sqrt(state.getLength())));
    return norm;
}

在索引时间我现在得到:

  • 文档 A 为 1.5(其字段中有 4 个标记)
  • 1.7071068 用于文档 B(其字段中有 2 个标记)

但是现在,当我查询这些文档时,我可以看到它们都具有与解释函数报告的相同的字段规范:

  • 1.5 = fieldNorm(field=titre, doc=0) 用于文档 A
  • 1.5 = fieldNorm(field=titre, doc=1) 用于文档 B

对我来说,现在这真的很奇怪,如果我在索引时使用一个明显很好的相似性来计算 fieldNorm,这给了我与令牌数量成正比的正确值,稍后,在查询时,所有这些丢失并且查询说两个文档具有相同的字段规范?

所以我的问题是:

  • 为什么 Similarity 的 computeNorm 方法报告的索引时间 fieldNorm 与查询说明报告的不一样?
  • 为什么,对于在索引时获得的两个不同 fieldNorm 值(通过相似度计算标准),我在查询时得到相同的 fieldNorm 值?

== 更新

好的,我在 Lucene's docs 中找到了一些东西,它澄清了我的一些问题,但不是全部:

但是,生成的规范值在存储之前被编码为单个字节。在搜索时,从索引目录中读取标准字节值并将其解码回浮点标准值。这种编码/解码虽然减少了索引大小,但也带来了精度损失——不能保证 decode(encode(x)) = x。例如,decode(encode(0.89)) = 0.75.

有多少精度损失?我们应该在不同的值之间设置一个最小差距,以便即使在重新计算精度损失后它们仍然保持不同?

【问题讨论】:

    标签: lucene indexing metrics


    【解决方案1】:

    encodeNormValue 的文档描述了编码步骤(这是丢失精度的地方),尤其是值的最终表示:

    编码使用 3 位尾数、5 位指数和 15 处的零指数点,因此表示从大约 7x10^9 到 2x10^-9 的值,具有大约一位有效十进制数字的精度。零也被表示。负数四舍五入为零。太大而无法表示的值会向下舍入到最大的可表示值。太小而无法表示的正值会四舍五入到可表示的最小正值。

    了解尾数只有 3 位的最相关部分,这意味着精度约为一位有效十进制数字。

    关于基本原理的重要说明是在您的报价结束后的几句话,Lucene 文档说:

    支持对规范值进行这种有损压缩的基本原理是,鉴于用户通过查询表达其真实信息需求的困难(和不准确),只有大的差异才重要

    【讨论】:

      猜你喜欢
      • 2011-03-27
      • 2017-12-08
      • 1970-01-01
      • 2011-11-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2023-03-12
      相关资源
      最近更新 更多