Xquery Marklogic搜索分数的控制有多严格?

Xquery Marklogic搜索分数的控制有多严格?,xquery,marklogic,Xquery,Marklogic,我们的数据库包含包含大量元数据的文档,包括这些文档之间的关系。虚构的例子: <document> <metadata> <document-number>ID 12345 : 2012</document-number> <publication-year>2012</publication-year> <cross-reference>ID 67890 : 1995</cros

我们的数据库包含包含大量元数据的文档,包括这些文档之间的关系。虚构的例子:

<document>
  <metadata>
    <document-number>ID 12345 : 2012</document-number>
    <publication-year>2012</publication-year>
    <cross-reference>ID 67890 : 1995</cross-reference>
    <cross-reference>ID 67890 : 1998</cross-reference>
    <cross-reference>ID 67891 : 2000</cross-reference>
    <cross-reference>ID 12345 : 2004</cross-reference>
    <supersedes>ID 12345 : 2004</supersedes>
    ...
  </metadata>
</document>
<document>
  <metadata>
    <document-number>ID 12345 : 2004</document-number>
    <publication-year>2004</publication-year>
    <cross-reference>ID 67890 : 1995</cross-reference>
    <cross-reference>ID 67890 : 1998</cross-reference>
    <cross-reference>ID 67891 : 2000</cross-reference>
    <cross-reference>ID 12345 : 2012</cross-reference>
    <cross-reference>ID 12345 : 2001</cross-reference>
    <superseded-by>ID 12345 : 2012</superseded-by>
    <supersedes>ID 12345 : 2001</supersedes>
    ...
  </metadata>
</document>

ID 12345:2012
2012
ID67890:1995
ID67890:1998
ID67891:2000
ID 12345:2004
ID 12345:2004
...
ID 12345:2004
2004
ID67890:1995
ID67890:1998
ID67891:2000
ID 12345:2012
ID12345:2001
ID 12345:2012
ID12345:2001
...
我们使用基于Marklogic搜索api的单框搜索,允许用户搜索这些文档。搜索语法描述了各种约束和搜索选项,但大多数情况下(默认情况下)它们通过定义为包含大多数元数据元素的字段进行搜索,并(在某种程度上)仔细选择权重(这里真正重要的是,
文档编号
的权重最高)

问题是,企业需要非常具体的结果排序,我想不出使用搜索api实现这一点的方法

造成问题的要求是,如果用户搜索与文档编号匹配(例如,他们搜索“12345”),则具有该文档编号的所有文档都应位于结果集的顶部,并按降序日期排序。让他们在结果集的顶端很容易<代码>文档编号的权重最高,因此按分数排序效果很好。问题是,按日期进行二次排序不起作用,因为即使所有
文档编号
匹配项的得分高于其他文档,但它们的得分并不相同,因此它们最终会按照搜索词在其余元数据中出现的频率排序;这一点都没有意义

我认为我们真正需要的是一种方法,只需通过匹配搜索词的最高加权元素来获得搜索api分数结果,而不参考文档中的任何其他匹配项。我看了一下评分算法,但没有看到这样的算法;我是否错过了什么,或者这是不可能的?显然,我们订购的不是
score
;如果有其他方法获得文档中单个最佳匹配的分数并将其用于排序,那就好了

有没有别的解决办法我都没想到

我曾想过做两次搜索(一次是在
文档编号
,另一次是在整个元数据树上),然后合并结果,但这似乎会给分页和性能带来很多麻烦。这就违背了使用搜索api的初衷


我应该补充一点,在结果集中有其他匹配项是正确的,因此我们不能只搜索
文档编号

我认为您已经达到了高级搜索API可以为您做的极限。不过,我有一些建议。这些不会是100%可靠的,但它们可能对业务来说已经足够好了。然后你就可以继续申请了。对不起,如果我听起来愤世嫉俗或不屑一顾,但我不相信微观管理搜索结果

最简单的方法是:重新排序内存中的第一页。第一个页面可能比您向用户显示的页面大一点。因为它的大小仍然有限,所以您可以在不受太大影响的情况下将规则变得相当复杂。这将解决您的“下降日期”问题。第1页的结果与第2页的结果不太匹配,但这可能已经足够好了

在复杂度的下一步,考虑使用文档质量来处理下行日期问题。除其他外,该方法也被使用。插入或更新每个文档时,使用从日期派生的数字设置文档质量。这可能是自1970年以来的几天、几周或几个月,或者使用其他固定日期。新的结果往往会浮到顶部。如果有任何其他的提升倾向于淹没基于日期的提升,你可能会接近你想要的

在分析查询以提取潜在的提升术语时,也可能有一些用处。如有必要,您可以对每个boosting术语开始递归运行
xdmp:exists(cts:search(doc(),$query))
,就像它是一个独立的查询一样。一旦找到
true()
result,就立即退出:这意味着您将用一个荒谬的高权重提升该查询项,使其浮到顶部

一旦知道了提升项是什么,就重写整个查询,将所有其他项权重设置为更低的值,甚至可能是0。权重越低,那些非提升术语对基于日期的质量和提升权重的干扰就越小。如果没有助推项,您可能需要进行其他调整。顺便说一句,所有这些都比听起来便宜。除了
xdmp:exists
调用之外,它只是内存中的表达式求值


不过,这些都只是提高分数的伎俩。他们不会让你绝对控制你想要的排名。根据我的经验,微观管理分数的尝试注定要失败。我敢打赌,无论您的业务经理怎么说,您的用户使用原始TF/IDF都会更高兴。

我认为您已经达到了高级搜索API为您所能做到的极限。不过,我有一些建议。这些不会是100%可靠的,但它们可能对业务来说已经足够好了。然后你就可以继续申请了。对不起,如果我听起来愤世嫉俗或不屑一顾,但我不相信微观管理搜索结果

最简单的方法是:重新排序内存中的第一页。第一个页面可能比您向用户显示的页面大一点。因为它的大小仍然有限,所以您可以在不受太大影响的情况下将规则变得相当复杂。这将解决您的“下降日期”问题。第1页的结果与第2页的结果不太匹配,但这可能已经足够好了

<