阅读 102

大数据利器Elasticsearch搜索之范围查询

这是我参与8月更文挑战的第24天,活动详情查看:8月更文挑战
本Elasticsearch相关文章的版本为:7.4.2

范围查询: 获取数值型、日期型和字符串型字段的特定范围的文档,对数字范围进行过滤尤其是在数据分析时会更有用。例如:获取价格大于20小于30的商品数据:
SQL:

select good from goods where price>20 and price<30;
复制代码

那么,在Elasticsearch中,实现上面的范围查询是使用range查询, 支持的关系运算符有:

运算符说明
gt大于(great than的首字母缩写)
lt小于(less than的首字母缩写)
gte大于等于(great than or equal的首字母缩写)
lte小于等于(less than or equal的首字母缩写)

数值型范围查询

构造点测试数据:

POST /num_range_test_index/_doc/1
{
  "price": 10
}

POST /num_range_test_index/_doc/2
{
  "price": 20
}

POST /num_range_test_index/_doc/3
{
  "price": 30
}

POST /num_range_test_index/_doc/4
{
  "price": 22
}

POST /num_range_test_index/_doc/5
{
  "price": 15
}
复制代码

所以上述的例子获取价格大于20小于30的商品数据在Elasticsearch中是这样查询的:

GET /num_range_test_index/_search
{
  "query": {
    "constant_score": {
      "filter": {
        "range": {
          "price": {
            "gte": 20,
            "lte": 30
          }
        }
      }
    }
  }
}
复制代码

返回的结果:

{
  "took" : 225,
  "timed_out" : false,
  "_shards" : {
    "total" : 1,
    "successful" : 1,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 3,
      "relation" : "eq"
    },
    "max_score" : 1.0,
    "hits" : [
      {
        "_index" : "num_range_test_index",
        "_type" : "_doc",
        "_id" : "2",
        "_score" : 1.0,
        "_source" : {
          "price" : 20
        }
      },
      {
        "_index" : "num_range_test_index",
        "_type" : "_doc",
        "_id" : "3",
        "_score" : 1.0,
        "_source" : {
          "price" : 30
        }
      },
      {
        "_index" : "num_range_test_index",
        "_type" : "_doc",
        "_id" : "4",
        "_score" : 1.0,
        "_source" : {
          "price" : 22
        }
      }
    ]
  }
}

复制代码

日期型范围查询

构造点测试数据:

POST /date_range_test_index/_doc/1
{
  "market_at": "2021-07-01"
}

POST /date_range_test_index/_doc/2
{
  "market_at": "2021-08-01"
}

POST /date_range_test_index/_doc/3
{
  "market_at": "2021-08-22"
}
复制代码

获取上市日期大于2021-08-01且小于2021-08-24的商品数据在Elasticsearch中是这样查询的:

GET /date_range_test_index/_search
{
  "query": {
    "constant_score": {
      "filter": {
        "range": {
          "market_at": {
            "gt": "2021-08-01",
            "lt": "2021-08-24"
          }
        }
      }
    }
  }
}
复制代码

返回的结果:

{
  "took" : 0,
  "timed_out" : false,
  "_shards" : {
    "total" : 1,
    "successful" : 1,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 1,
      "relation" : "eq"
    },
    "max_score" : 1.0,
    "hits" : [
      {
        "_index" : "date_range_test_index",
        "_type" : "_doc",
        "_id" : "3",
        "_score" : 1.0,
        "_source" : {
          "market_at" : "2021-08-22"
        }
      }
    ]
  }
}
复制代码

字符串型范围查询

字符串的范围查询是按照字符序进行排序的。例如'a'<'b'。 构造点测试数据:

POST /string_range_test_index/_doc/1
{
  "goods_name": "apple"
}

POST /string_range_test_index/_doc/2
{
  "goods_name": "banana"
}

POST /string_range_test_index/_doc/3
{
  "goods_name": "orange"
}
复制代码

获取商品名大于小于的商品数据在Elasticsearch中是这样查询的:

GET /string_range_test_index/_search
{
  "query": {
    "constant_score": {
      "filter": {
        "range": {
          "goods_name": {
            "gte": "a",
            "lt": "c"
          }
        }
      }
    }
  }
}
复制代码

返回的结果:

{
  "took" : 0,
  "timed_out" : false,
  "_shards" : {
    "total" : 1,
    "successful" : 1,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 2,
      "relation" : "eq"
    },
    "max_score" : 1.0,
    "hits" : [
      {
        "_index" : "string_range_test_index",
        "_type" : "_doc",
        "_id" : "1",
        "_score" : 1.0,
        "_source" : {
          "goods_name" : "apple"
        }
      },
      {
        "_index" : "string_range_test_index",
        "_type" : "_doc",
        "_id" : "2",
        "_score" : 1.0,
        "_source" : {
          "goods_name" : "banana"
        }
      }
    ]
  }
}
复制代码
文章分类
后端
文章标签