0

当我在 elasticsearch 上进行搜索时,我想操纵我得到的分数。我已经使用了 boost 选项,但它并没有给我想要的结果。经过一番阅读,我认为 function_score 查询是我的问题的解决方案。我了解它是如何工作的,但我不知道如何更改当前查询以将其与 function_score 查询一起使用。

"query": {
"filtered": {
    "query": {
        "bool": {
            "should": [{
                "multi_match": {
                    "type": "most_fields",
                    "query": "paus",
                    "operator": "and",
                    "boost": 2,
                    "fields": [
                        "fullname^2",
                        "fullname.folded",
                        "alias^2",
                        "name^2"
                    ],
                    "fuzziness": 0
                }
            }, {
                "multi_match": {
                    "type": "most_fields",
                    "query": "paus",
                    "operator": "and",
                    "boost": 1.9,
                    "fields": [
                        "taggings.tag.name^1.9",
                        "function",
                        "relations.master.name^1.9",
                        "relations.master.first_name^1.9",
                        "relations.master.last_name^1.9",
                        "relations.slave.name^1.9",
                        "relations.slave.first_name^1.9",
                        "relations.slave.last_name^1.9"
                    ],
                    "fuzziness": 0
                }
            }, {
                "multi_match": {
                    "type": "most_fields",
                    "query": "paus",
                    "operator": "and",
                    "fields": [
                        "fullname",
                        "alias",
                        "name"
                    ],
                    "boost": 0.2,
                    "fuzziness": 1
                }
            }, {
                "match": {
                    "extra": {
                        "query": "paus",
                        "fuzziness": 0,
                        "boost": 0.1
                    }
                }
            }]
        }
    },
    "filter": {
        "bool": {
            "must": [
                {
                    "terms": {
                        "type": ["Person"]
                    }
                },
                {
                    "term": {
                        "deleted": false
                    }
                }
            ]
        }
    }
}

如您所见,我们有四种匹配项。

  • Boost 2:当名称完全匹配时
  • Boost 1.9:当标签上有完全匹配时
  • Boost 0.2:当名称匹配但一个字符写错时
  • Boost 0.1:当额外(描述)字段中有匹配项时

我面临的问题是一个字符写错并且没有标记得分高于正确标记和整个单词写错的匹配。那应该是另一种方式...

任何帮助,将不胜感激 :)

4

1 回答 1

1

对此没有明确的答案。你最好的朋友是解释 API,它会告诉你每个文档score是如何计算的。

要记住的最重要的事情boost只是计算分数时考虑的因素之一。从文档

实际上,没有简单的公式可以确定特定查询子句的“正确”提升值。这是一个试试看的问题。请记住,提升只是相关性得分中涉及的因素之一;它必须与其他因素竞争

如果您通过TheoryLucene 的 Practical Scoring Function对您有很大帮助。这是Lucene使用的公式。

score(q,d)  =  
            queryNorm(q)  
          · coord(q,d)    
          · ∑ (           
                tf(t in d)   
              · idf(t)²      
              · t.getBoost() 
              · norm(t,d)    
            ) (t in q) 

现在,您没有得到预期结果的几个原因之一可能是norm(t,d)idf(t)²。例如,如果您的extra字段为paus me,而其他字段的内容类似于my name is some paus somethingfield length norm,那将提供norm(t.d)更高的价值。此外,如果您说 10000 个文档并且只有一个文档在字段中暂停extra,那会使逆文档频率非常高,因为它是按idf(t) = 1 + log ( numDocs / (docFreq + 1))此处计算的numDocs=10000docFreq=1并且该值将被平方。我的数据集中正好有这个问题。

模糊查询得分较高可能与这个问题有关,这基本上是一个Lucene 问题。这已在最新版本中修复。

一种可能有效的方法是给最后两个子句加上 constant_score 并说前两个子句增加5将有助于理解。

尝试逐步解决此问题,从两个子句开始,查看 的输出explain api,然后尝试三个,最后全部四个。也删除field boostingquery boost仅尝试。慢慢你就会明白了。

我希望这有帮助!!

于 2015-12-31T16:50:39.377 回答