参考地址:https://my.oschina.net/u/1792341/blog/911383
https://www.cnblogs.com/wenbronk/p/6432990.html

导入所需maven依赖

  1. <properties>
  2. <elasticsearch.version>7.2.1</elasticsearch.version>
  3. </properties>
  4. <dependency>
  5. <groupId>org.elasticsearch</groupId>
  6. <artifactId>elasticsearch</artifactId>
  7. <version>${elasticsearch.version}</version>
  8. </dependency>
  9. <dependency>
  10. <groupId>org.elasticsearch.client</groupId>
  11. <artifactId>elasticsearch-rest-high-level-client</artifactId>
  12. <version>${elasticsearch.version}</version>
  13. </dependency>

连接服务器

  1. private static RestHighLevelClient restHighLevelClient = new RestHighLevelClient(
  2. RestClient.builder(
  3. new HttpHost("192.168.1.100", 9200, "http")));

查询介绍

Match查询
此查询将文本或短语与一个或多个字段的值相匹配。例如,

  1. POST /schools*/_search
  2. {
  3. "query":{
  4. "match" : {
  5. "city":"pune"
  6. }
  7. }
  8. }

multi_match查询
此查询将文本或短语与多个字段匹配。例如

  1. POST /schools*/_search
  2. {
  3. "query":{
  4. "multi_match" : {
  5. "query": "hyderabad",
  6. "fields": [ "city", "state" ]
  7. }
  8. }
  9. }

Query String查询
该查询使用查询解析器和query_string关键字。例如

  1. POST /schools/_search
  2. {
  3. "query":{
  4. "query_string":{
  5. "query":"good faculty"
  6. }
  7. }
  8. }

Term查询
这些查询主要处理数字、日期等结构化数据。例如

  1. POST /schools/_search
  2. {
  3. "query":{
  4. "term":{"zip":"176115"}
  5. }
  6. }

Range查询
该查询用于查找值在值范围之间的对象。为此,我们需要使用如下运算符

  • gte:大于等于
  • gt:大于
  • lte:小于等于
  • lt:小于

    举个例子:

  1. POST /schools*/_search
  2. {
  3. "query":{
  4. "range":{
  5. "rating":{
  6. "gte":3.5
  7. }
  8. }
  9. }
  10. }

其他类型的term级查询有:

  • Exists查询:判断某个字段具有非空值。
  • Missing查询:与Exists查询相反,该查询搜索没有特定字段或字段值为空的对象。
  • Wildcard or regexp查询:该查询使用正则表达式来查找对象中的模式。
  • Type query查询:特定类型的文档。例如,
  1. POST /schools*/_search
  2. {
  3. "query":{
  4. "type" : {
  5. "value" : "school"
  6. }
  7. }
  8. }

复合查询
这些查询是通过使用布尔运算符(如and、or、not或for不同索引或具有函数调用等)彼此合并的不同查询的集合。例如

  1. POST /schools*/_search
  2. {
  3. "query":{
  4. "filtered":{
  5. "query":{
  6. "match":{
  7. "state":"UP"
  8. }
  9. },
  10. "filter":{
  11. "range":{
  12. "rating":{
  13. "gte":4.0
  14. }
  15. }
  16. }
  17. }
  18. }
  19. }

Joining查询
这些查询用于包含多个映射或文档的情况。有两种类型的joining查询:
嵌套查询
这些查询处理嵌套映射(您将在下一章中了解更多)。
has_child和has_parent查询
这些查询用于检索在查询中匹配的文档的子文档或父文档。例如,

  1. POST /tutorials/_search
  2. {
  3. "query":
  4. {
  5. "has_child" : {
  6. "type" : "article", "query" : {
  7. "match" : {
  8. "Text" : "This is article 1 of chapter 1"
  9. }
  10. }
  11. }
  12. }
  13. }

地理位置查询
这些查询处理地理位置,这些查询有助于找到指定位置附近的学校或任何其他地点。您需要使用地理点数据类型。例如,

  1. POST /schools*/_search
  2. {
  3. "query":{
  4. "filtered":{
  5. "filter":{
  6. "geo_distance":{
  7. "distance":"100km",
  8. "location":[32.052098, 76.649294]
  9. }
  10. }
  11. }
  12. }
  13. }

总结

match query搜索的时候,首先会解析查询字符串,进行分词,然后查询,而term query,输入的查询内容是什么,就会按照什么去查询,并不会解析查询内容,对它分词。
**简单的matchQuery 查询的内容会通过分词,分词后的数据进行检索,只要包含其中一个分词就会被检索出来

  1. searchRequestBuilder.setQuery(QueryBuilders.matchQuery("fieldD", "bigData is magic"));
  1. matchPhraseQuery 查询的内容通过分词,严格按照分词的出现的顺序进行查询,也就是必须包含所有分词,且出现数据一致

    1. searchRequestBuilder.setQuery(QueryBuilders.matchPhraseQuery("fieldD", "bigData spark is magic"));

    询的字段是进行分词索引的,如果不是分词索引则不生效, 如果只是查询 bigData magic ,则这种查询是查询不到的,需要完全匹配,如果想要查询到,需要设置slop(2),需要这样查询

    1. searchRequestBuilder.setQuery(QueryBuilders.matchPhraseQuery("fieldD", "bigData spark is magic").slop(2))
  2. termQuery 词精确查询,fieldD 分词后包含 bigData的term的文档

    1. searchRequestBuilder.setQuery(QueryBuilders.termQuery("fieldD", "bigData"));
  3. terms Query 多term查询,查询fieldD 包含 bigData spark或storm 中的任何一个或多个的文档

    1. searchRequestBuilder.setQuery(QueryBuilders.termsQuery("fieldD", "bigData","spark","storm"));
  4. rangeQuery 范围查询字段fieldB 大于20并且小于50 包含上下界

    1. searchRequestBuilder.setQuery(QueryBuilders.rangeQuery("filedB").gt("20").lt("50").includeLower(true).includeUpper(true));
  5. prefixQuery 匹配分词前缀 如果字段没分词,就匹配整个字段前缀

    1. searchRequestBuilder.setQuery(QueryBuilders.prefixQuery("fieldD","spark"));
  6. wildcard query 通配符查询,支持* 任意字符串;?任意一个字符

    1. searchRequestBuilder.setQuery(QueryBuilders.wildcardQuery("fieldD","spark*"));
  7. Fuzzy query 分词模糊查询,通过增加fuzziness 模糊属性,来查询term 如下 能够匹配 fieldD 为 spar park spark前或后加一个字母的term的 文档 fuzziness 的含义是检索的term 前后增加或减少n个单词的匹配查询

    1. searchRequestBuilder.setQuery(QueryBuilders.fuzzyQuery("fieldD","spark").fuzziness(Fuzziness.ONE));
  8. QueryStringQueryBuilder 使用的默认的分词导致的。

在没有给QueryStringQueryBuilder 指定特定的分词器时,ES会用默认的analyzer来处理,也就是名字(logical name)为default, default_index, default_search的analyzer。
ES内置的一些analyzer。

analyzer logical name description
standard analyzer standard standard tokenizer, standard filter, lower case filter, stop filter
simple analyzer simple lower case tokenizer
stop analyzer stop lower case tokenizer, stop filter
keyword analyzer keyword 不分词,内容整体作为一个token(not_analyzed)
pattern analyzer whitespace 正则表达式分词,默认匹配\W+
language analyzers lang 各种语言
snowball analyzer snowball standard tokenizer, standard filter, lower case filter, stop filter, snowball filter
custom analyzer custom 一个Tokenizer, 零个或多个Token Filter, 零个或多个Char Filter


这个情况会使ES检索时,会对中文进行最小粒度的切分,例如:

  1. new QueryStringQueryBuilder("客服").field("title").defaultOperator(Operator.AND);

则ES检索时,会将“客服” 拆分成 “客”,“服”,检索的结果为title中有 “客”,“服”两个字的即可,不需要两个字相邻,如果需要检索包含“客服”的,加上 双引号 表示强制要求 拆分一起,则需要写成:

  1. new QueryStringQueryBuilder("\""+"客服"+"\"").field("title").defaultOperator(Operator.AND);