为什么使用term查询查询elasticsearch时,搜索结果会有差异?

如何解决为什么使用term查询查询elasticsearch时,搜索结果会有差异?

我最近开始学习 elasticsearch,我的查询搜索结果有所不同。下面提供了名为“products”的索引的映射(我正在粘贴来自 Kibana 控制台工具的响应):

    {
    "products" : {
"mappings" : {
  "properties" : {
    "in_stock" : {
      "type" : "long"
    },"name" : {
      "type" : "text","fields" : {
        "keyword" : {
          "type" : "keyword","ignore_above" : 256
        }
      }
    },"price" : {
      "type" : "long"
    },"tags" : {
      "type" : "text","ignore_above" : 256
        }
      }
    }
  }
}
}
}

索引中的数据如下(我粘贴的是我的 Kibana 控制台工具的响应):

{
   "took" : 0,"timed_out" : false,"_shards" : {
  "total" : 1,"successful" : 1,"skipped" : 0,"Failed" : 0
  },"hits" : {
"total" : {
  "value" : 16,"relation" : "eq"
},"max_score" : 1.0,"hits" : [
  {
    "_index" : "products","_type" : "_doc","_id" : "202","_score" : 1.0,"_source" : {
      "name" : "vegetable Chopper","price" : 10,"in_stock" : 250,"tags" : [
        "kitchen appliances","vegetable slicer","chopper"
      ]
    }
  },{
    "_index" : "products","_id" : "203","_source" : {
      "name" : "dish Washer","price" : 90,"in_stock" : 60,"electrical","electric washer"
      ]
    }
  },"_id" : "205","_source" : {
      "name" : "Microwave Oven","price" : 100,"in_stock" : 50,"electricals","oven","oven toaster","microwave"
      ]
    }
  },"_id" : "206","_source" : {
      "name" : "mixer Grinder","price" : 55,"in_stock" : 130,"mixer","grinder","juicer","food processor"
      ]
    }
  },"_id" : "207","_source" : {
      "name" : "Fruit Juicer","price" : 40,"in_stock" : 100,"electicals","electric juicer","juice maker"
      ]
    }
  },"_id" : "208","_source" : {
      "name" : "Knife Set","price" : 15,"tags" : [
        "kitchen knife","steel knives","cutlery"
      ]
    }
  },"_id" : "209","_source" : {
      "name" : "Rice Maker","price" : 85,"electric rice cooker","electric pressure cooker"
      ]
    }
  },"_id" : "210","_source" : {
      "name" : "Induction Cooktop","price" : 30,"in_stock" : 150,"hot plate heater","electric hot place","induction cooker","induction stove"
      ]
    }
  },"_id" : "211","_source" : {
      "name" : "Coffee Maker","price" : 50,"electricals"
      ]
    }
  },"_id" : "212","_source" : {
      "name" : "Wine Glasses Set","in_stock" : 70,"tags" : [
        "kitchen and dining","glassware","stemware"
      ]
    }
  },"_id" : "213","_source" : {
      "name" : "Dinner Set","in_stock" : 40,"crockery","full dinner set"
      ]
    }
  },"_id" : "214","_source" : {
      "name" : "Whiskey Glasses Set","price" : 60,"whiskey glasses","old fashioned glass","rocks glass","short tumbler"
      ]
    }
  },"_id" : "215","_source" : {
      "name" : "Mug And Saucer Set","price" : 35,"mug set","mugs and saucer","crockery set"
      ]
    }
  },"_id" : "201","_source" : {
      "name" : "Milk Frother","price" : 25,"in_stock" : 15,"milk"
      ]
    }
  },"_id" : "200","_source" : {
      "name" : "Espresso Maker","price" : 180,"in_stock" : 5,"coffee maker"
      ]
    }
  },"_id" : "204","_source" : {
      "name" : "Pressure Fryer","price" : 120,"tags" : [
        "air fryer","kitchen appliances","electric fryer","fryer","health fryer"
      ]
    }
  }
]
  }
}

在使用下面的查询查询数据时,我只匹配了 6 条记录: 查询 - 1

GET /products/_search
{
  "query": {"terms" : {"tags": ["kitchen appliances","electricals"]}}
}

匹配的文档 id 为 (201,205,206,209,210,211)

当我执行以下查询时,我匹配了 11 条记录: 查询-2

GET /products/_search
{
  "query": {"terms" : {"tags.keyword": ["kitchen appliances","electricals"]}}
}

与第二个查询匹配的文档 ID 为:(200,201,202,203,204,207,211)

有人能解释一下这两个查询间的区别是什么吗?为什么 Query-1 是 Query-2 的子集,即使两个查询都在同一个字段上执行?

解决方法

如果您有 match 类型的字段,最好使用 text 查询。

term query 不对术语进行任何分析。它返回包含精确术语匹配文档的文档。

terms query 在精确的条件下工作。它返回那些具有 1 个或多个精确术语的文档。


问题 1:

{
  "query": {
    "terms": {
      "tags": [
        "kitchen appliances","electricals"
      ]
    }
  }
}

搜索结果是

"hits": [
      {
        "_index": "67155973","_type": "_doc","_id": "3","_score": 1.0,"_source": {
          "name": "Microwave Oven","price": 100,"in_stock": 50,"tags": [
            "kitchen appliances","electricals","oven","oven toaster","microwave"
          ]
        }
      },{
        "_index": "67155973","_id": "4","_source": {
          "name": "Mixer Grinder","price": 55,"in_stock": 130,"mixer","grinder","juicer","food processor"
          ]
        }
      },"_id": "7","_source": {
          "name": "Rice Maker","price": 85,"in_stock": 60,"electric rice cooker","electric pressure cooker"
          ]
        }
      },"_id": "8","_source": {
          "name": "Induction Cooktop","price": 30,"in_stock": 150,"hot plate heater","electric hot place","induction cooker","induction stove"
          ]
        }
      },"_id": "9","_source": {
          "name": "Coffee Maker","price": 50,"in_stock": 100,"electricals"
          ]
        }
      },"_id": "14","_source": {
          "name": "Milk Frother","price": 25,"in_stock": 15,"milk"
          ]
        }
      }
    ]

documentation

中所述

词条查询不分析搜索词。只查询词条 搜索您提供的确切术语。这意味着术语查询可能 搜索文本字段时返回的结果很差或没有结果。


问题 2:

{
  "query": {
    "terms": {
      "tags.keyword": [
        "kitchen appliances","electricals"
      ]
    }
  }
}

在上述查询中,您使用的是 tags.keyword 字段,该字段使用关键字分析器而不是标准分析器。此处查询搜索确切的术语,即 "kitchen appliances" OR "electricals",因此返回 11 个文档。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其他元素将获得点击?
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。)
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbcDriver发生异常。为什么?
这是用Java进行XML解析的最佳库。
Java的PriorityQueue的内置迭代器不会以任何特定顺序遍历数据结构。为什么?
如何在Java中聆听按键时移动图像。
Java“Program to an interface”。这是什么意思?
Java在半透明框架/面板/组件上重新绘画。
Java“ Class.forName()”和“ Class.forName()。newInstance()”之间有什么区别?
在此环境中不提供编译器。也许是在JRE而不是JDK上运行?
Java用相同的方法在一个类中实现两个接口。哪种接口方法被覆盖?
Java 什么是Runtime.getRuntime()。totalMemory()和freeMemory()?
java.library.path中的java.lang.UnsatisfiedLinkError否*****。dll
JavaFX“位置是必需的。” 即使在同一包装中
Java 导入两个具有相同名称的类。怎么处理?
Java 是否应该在HttpServletResponse.getOutputStream()/。getWriter()上调用.close()?
Java RegEx元字符(。)和普通点?