在ES中使用正确有意义的查询语句是很重要的,可以方便、快速的从大量数据中找到想要的数据。所以写好一个查询语句是必不可少的。
ES分词器
分词器是ES搜索引擎的核心特点,合理了解并使用可以发挥ES最大的效率。后面很多查询也有关,所以应该重点了解分词器。
对于存入(Index)中的各个字段(Term),ES内部都会有分词器对其分词,然后将这个分词结果保存,方便未来使用。也可以直接使用。
访问分词器使用_analyze,默认是英文分词器,中文可以下载其他分词器使用。
点击查看代码
POST http://ip:prot/_analyze
{
"analyzer": "standard",
"text": "This is a test doc"
}
结果会返回被分好词的单词,还有偏移量。
ES查询
1、match
下面是es中全量查询,查询所有数据,默认size为10,比较消耗细性能,建议少使用。
GET test/doc/_search
{
"query":{
"match_all": {
}
}
}
1.1 match_phrase 短语查询
对于获取想要的数据进行部分查询,使用下面例子中的语法。因为es中是使用分词器作为核心,所以返回结果中会有name中包含jacky的所有数据。而不是name==="jacky"
的数据。
GET test1/doc/_search
{
"query":{
"match":{
"name":"jacky"
}
}
}
查看结果示例
"hits" : [
{
"_index" : "test",
"_type" : "doc",
"_id" : "1",
"_score" : 0.68324494,
"_source" : {
"name" : "jacky"
}
},
{
"_index" : "test",
"_type" : "doc",
"_id" : "1",
"_score" : 0.68324434,
"_source" : {
"name" : "jacky chen"
}
},
...... ]
1.2 term 精确查询
但是如果想查询,正好name为jacky不多不少,该怎么查询呢?
使用term(精确匹配查询)可以获取想要的结果。
{
"query": {
"term": {
"name.keyword": "jacky"
}
}
}
使用term精确查询,就可以返回精确匹配的值。
1.3 multi_match bool 多字段查询
多字段查询可以同时匹配多个字段,并且只返回目标的key-value。
{
"name":"jacky",
"age":16,
"addr":"XX-XX",
"job":"student",
......
}
例如某index中存贮的类似格式的大量数据,但是我们只需要其中name和age属性。如果使用之前的查询方式,addr和job以及其他的属性会一并返回。大大减少了数据处理效率,以及服务器查询压力。
这时,多字段查询的优势就体现出来了。
GET test/doc/_search
{
"query": {
"multi_match": {
"query": "search",
"fields": ["name","age"]
}
}
}
除了使用multi_match
查询以外,还有bool
查询
查看bool查询代码
GET test/doc/_search
{
"query": {
"bool": {
"must": [
{ "match": { "name": "jacky" } },
{ "match": { "age": "16" } }
]
}
}
}
1.4排序查询
当查询一些类似字典或者数字类型的数据时候,希望查出来就已经是顺(逆)序,就会使用到排序查询
倒叙排序
GET test/doc/_search
{
"query": {
"match_all": {}
},
"sort": [
{
"age": {
"order": "desc"
}
}
]
}
升序排序
GET test/doc/_search
{
"query": {
"match_all": {}
},
"sort": [
{
"age": {
"order": "asc"
}
}
]
}
1.5结果过滤
当了解使用查询结果排序后,结果过滤也是很重要的。
PUT test/doc/_search
{
"name":"jacky",
"age":16,
"from": "gu",
"desc": "good good study,day day up",
"tags": ["好好学习", "天天向上"]
}
如果只需要其中的name和age属性,使用结果过滤可以提高查询效率。
GET test3/doc/_search
{
"query": {
"match": {
"name": "jacky"
}
},
"_source": ["name","age"]
}
1.6 时间范围查询
先了解范围查询的符号
符号 | 含义 |
---|---|
gte | greater-than or equal to, 大于或等于 |
gt | greater-than, 大于 |
lte | less-than or equal to, 小于或等于 |
lt | less-than, 小于 |
例子:查询网站中最近一天发布的博客: |
GET website/_search
{
"query": {
"range": {
"post_date": {
"gte": "now-1d/d",
// 当前时间的上一天, 四舍五入到最近的一天
"lt": "now/d"
// 当前时间, 四舍五入到最近的一天
}
}
}
}
表达式 | 含义 | 表达式 | 含义 |
---|---|---|---|
y | 年 | M | 月 |
w | 星期 | d | 天 |
h | 小时 | H | 小时 |
m | 分钟 | s | 秒 |
now
表达式可以获取当前的时间
所以得到的数据就是在昨天到今天之间的数据。