ElasticSearch -在布尔查询中仅增强一次

bzzcjhmw  于 2023-03-07  发布在  ElasticSearch
关注(0)|答案(2)|浏览(156)

我真的不知道该如何表达我的问题,但以下面的对象为例:

{
  "pricing": [
    {"cost": 5000, "style": "fixed"},
    {"cost_min": 100, "cost_max": 500, "style": "range"},
    {"style": "fixed"}
  ]
}

我想做的是(伪逻辑):

Boost score by X IF exists(pricing.cost) OR (exists(pricing.cost_min) AND exists(pricing.cost_max))

这是我目前拥有的:

"bool": {
    "should": [
        {
            "exists": {
                "field": "pricing.cost",
                "boost": 2
            }
        },
        {
            "bool": {
                "should": [
                    {
                        "exists": {
                            "field": "pricing.cost_min",
                        }
                    },
                    {
                        "exists": {
                            "field": "pricing.cost_max",
                        }
                    }
                ],
                "minimum_should_match": 2,
            }
        }
    ],
    "minimum_should_match": 1,
    "boost": 1
}

它工作正常,除了我给它的示例对象提升了“两次”,给出了4分,但实际上我想要2分

pzfprimi

pzfprimi1#

默认情况下,每个子句应用boost = 1。如果您希望boost为2而不是4,则必须在pricing.cost_min和pricing.cost_max中将boost设置为0。

rslzwgfq

rslzwgfq2#

如果您使用nested作为价格,则此文档的得分为2。但这也会更改您的查询。以下是示例文档的完整示例:

PUT pricing_with_nested
{
  "mappings": {
    "properties": {
      "pricing":{
        "type": "nested"
      }
    }
  }
}

POST pricing_with_nested/_doc
{
  "pricing": [
    {"cost": 5000, "style": "fixed"},
    {"cost_min": 100, "cost_max": 500, "style": "range"},
    {"style": "fixed"}
  ]
}

GET pricing_with_nested/_search
{
  "explain": true, 
  "query": {
    "nested": {
      "path": "pricing",
      "query": {
        "bool": {
          "should": [
            {
              "exists": {
                "field": "pricing.cost",
                "boost": 2
              }
            },
            {
              "bool": {
                "should": [
                  {
                    "exists": {
                      "field": "pricing.cost_min"
                    }
                  },
                  {
                    "exists": {
                      "field": "pricing.cost_max"
                    }
                  }
                ],
                "minimum_should_match": 2
              }
            }
          ],
          "minimum_should_match": 1,
          "boost": 1
        }
      }
    }
  }
}

编辑:
我想给出一些细节来解释为什么当你使用正常数据类型时,给4而不是2作为分数。让我们从你的查询开始。当你使用"explain": true作为你的第一个查询时,你会看到下面对你的文档结果的解释。

"_explanation": {
   "value": 4,
   "description": "ConstantScore(*:*)^4.0",
   "details": []
}

这是因为exists查询将使用一个常数score,并且主bool的should的每个子句,score将乘以boost。让我们看看如果我们可以用nested改变字段类型的结果。解释将改变如下:

{
  "_explanation": {
    "value": 2,
    "description": "Score based on 2 child docs in range from 0 to 2, best match:",
    "details": [
      {
        "value": 2,
        "description": "sum of:",
        "details": [
          {
            "value": 2,
            "description": "sum of:",
            "details": [
              {
                "value": 2,
                "description": "ConstantScore(FieldExistsQuery [field=pricing.cost])^2.0",
                "details": []
              }
            ]
          },
          {
            "value": 0,
            "description": "match on required clause, product of:",
            "details": [
              {
                "value": 0,
                "description": "# clause",
                "details": []
              },
              {
                "value": 1,
                "description": "_nested_path:pricing",
                "details": []
              }
            ]
          }
        ]
      }
    ]
  }
}

正如你从这段文字中看到的,Score based on 2 child docs in range from 0 to 2, best match:。每个得分将被嵌套对象分开,最后的查询将选择最好的得分。

相关问题