ES详解 - 查询:DSL查询之Term详解
大熊•
Term查询引入
如前文所述,查询分基于文本查询和基于词项的查询:
Term
(词项)是ES中表达语义的最小单位,搜索和利用统计语言模型进行自然语言处理都需要处理Term
, 主要包含的查询类型有:Term Query
/Range Query
/Exist Query
/Prefix Query
/Wildcard Query
。
-
特点1:在ES中,Term查询对输入不做分词。换句话说,它会将输入作为一个整体,在倒排索引中查找准确的词项,并且使用相关度算分公式为每个包含该词项的文档进行相关度算分 - 例如"Apple Store"。 精确匹配注意是大小完全匹配的。
-
特点2:可以使用
Constant Score
将查询转换成一个Filtering
,避免算分,并利用缓存,提高性能。
Query
基于全文的查询, 主要包含的查询类型有:Match Query
/Match Phrase Query
/Query String Query
具有以下的特点:
-
特点1:索引和搜索时都会进行分词,查询字符串先传到一个合适的分词器,然后生成一个待查询的词项列表。
-
特点2:查询会对每个词项进行底层的查询,再将结果进行合并,还会为每个文档生成一个算分。
Term查询
本文
字段是否存在: exist
由于多种原因,文档字段的索引值可能不存在:
- 源JSON中的字段是
null
或[]
- 该字段已
"index" : false
在映射中设置 - 字段值的长度超出
ignore_above
了映射中的设置 - 字段值格式错误,并且
ignore_malformed
已在映射中定义
所以exist
表示查找是否存在字段。
id查询: ids
ids 即对id查找, 也就是对 _id
值的聚合查找。
{
"query": {
"ids": {
"values": [3, 1]
}
}
}
前缀:prefix
通过前缀查找某个字段
{
"query": {
"prefix": {
"name": {
"value": "Jan"
}
}
}
}
分词匹配:term
前文最常见的根据分词查询
{
"query": {
"term": {
"programming_languages": "php"
}
}
}
多个分词匹配:terms
按照读个分词term
匹配,它们是or
的关系
GET /test-dsl-term-level/_search
{
"query": {
"terms": {
"programming_languages": ["php","c++"]
}
}
}
按某个数字字段分词匹配:term set
设计这种方式查询的初衷是用文档中的数字字段动态匹配查询满足term的个数
GET /test-dsl-term-level/_search
{
"query": {
"terms_set": {
"programming_languages": {
"terms": [ "java", "php" ],
"minimum_should_match_field": "required_matches"
}
}
}
}
通配符:wildcard
通配符匹配,比如*
GET /test-dsl-term-level/_search
{
"query": {
"wildcard": {
"name": {
"value": "D*ai",
"boost": 1.0,
"rewrite": "constant_score"
}
}
}
}
范围:range
常常被用在数字或者日期范围的查询
GET /test-dsl-term-level/_search
{
"query": {
"range": {
"required_matches": {
"gte": 3,
"lte": 4
}
}
}
}
正则:regexp
通过正则表达式查询 以"Jan"开头的name字段
GET /test-dsl-term-level/_search
{
"query": {
"regexp": {
"name": {
"value": "Ja.*",
"case_insensitive": true
}
}
}
}
模糊匹配:fuzzy
官方文档对模糊匹配:编辑距离是将一个术语转换为另一个术语所需的一个字符更改的次数。这些更改可以包括:
- 更改字符(
box → fox
) - 删除字符(
black → lack
) - 插入字符(
sic → sick
) - 转置两个相邻字符(
act → cat
)
GET /test-dsl-term-level/_search
{
"query": {
"fuzzy": {
"remarks": {
"value": "hell"
}
}
}
}
本文使用到的查询数据
PUT /test-dsl-term-level
{
"mappings": {
"properties": {
"name": {
"type": "keyword"
},
"programming_languages": {
"type": "keyword"
},
"required_matches": {
"type": "long"
}
}
}
}
POST /test-dsl-term-level/_bulk
{ "index": { "_id": 1 }}
{"name": "Jane Smith", "programming_languages": [ "c++", "java" ], "required_matches": 2}
{ "index": { "_id": 2 }}
{"name": "Jason Response", "programming_languages": [ "java", "php" ], "required_matches": 2}
{ "index": { "_id": 3 }}
{"name": "Dave Pdai", "programming_languages": [ "java", "c++", "php" ], "required_matches": 3, "remarks": "hello world"}