[ElasticSearch]间隔搜索IntervalsQuery及JavaSDK简单调用_小鱼收藏夹的博客-程序员信息网_elasticsearch interval

技术标签: elasticsearch  

1) 概念

* intervals query 允许用户精确控制查询词在文档中出现的先后关系,实现了对terms顺序、terms之间的距离以及它们之间的包含关系的灵活控制
    通过intervals query(间隔搜索) 我们可以完成各个terms在于不同位置的灵活搜索
    
* 下面来举一个例子来说明间隔搜索的适用场景:
    我们在某个索引中3个包含my_text字段的文档

    文档1:  {"my_text":"curry bad shooter.... "}
    文档2: {"my_text":"curry good shooter....."}
    文档3:  {"my_text":"curry best shooter...."}


    通过间隔搜索,我可以明确的表示 我不想看到curry和shooter之间存在 bad的文档
    我还可以明确的表示,我必须看到curry和shooter之间 存在 某个词 的文档
    我也可以明确的表示,curry必须在best之前等等一系列功能
    
* 例如 我不想看到curry和shooter之间存在bad,DSL如下:
 

{
  "query": {
    "intervals": {
      "content": {
        "match": {
          "query": "curry shooter",
          "ordered": true,
          "filter": {
            "not_containing": {
              "match": {
                "query": "bad"
              }
            }
          }
        }
      }
    }
  }
}

2) 参数

* 首先来看一个略复杂的DSL语句并简单理解后学习参数

POST _search
{
  "query": {
    "intervals" : {
      "my_text" : {
        "all_of" : {
          "ordered" : true,
          "intervals" : [
            {
              "match" : {
                "query" : "stephen curry",
                "max_gaps" : 0,
                "ordered" : true
              }
            },
            {
              "any_of" : {
                "intervals" : [
                  { "match" : { "query" : "best shooter" } },
                  { "match" : { "query" : "cute champion" } }
                ]
              }
            }
          ]
        },
        "boost" : 2.0
      }
    }
  }
}

简单概述上方语句,像包含"stephen curry is best shooter"或者"stephen cuury is cute champion"都会被检索到,但是 "best shooter who is stephen curry" 不会被检索到,因为我们通过ordered参数明确定义了多个intervals的顺序。


你一定看到了all_of并不解,此处简单解释,在某些时候 一个intervals无法满足我们的要求,那么我们可以编写多个intervals,将其放在all_Of内部,表示所有的intervals都要生效,同样内部可以再次嵌套,比如any_of 表示内部的多个intervals只需满足其一即可。

  • match

参数 描述
query 用户查询的字符串
max_gaps 字符串中多个词之间的的最大词间距,超过最大间距的将不会被检索到;默认值是-1,即无距离限制,设置为0的话,query中的字符串必须彼此相连不能拆分
ordered query中的字符串是否需要有序显示,默认值是false,即不考虑先后顺序,该参数推荐为true,手动控制词间位置顺序
analyzer 对query参数中的字符串使用什么分词器,默认使用mapping时该field配置的 search_analyzer
filter intervals独有的过滤语法,下方有说明
  • all_of

参数 描述
intervals 一个interval集合,集合里面的所有match需要同时在一个文档数据上同时满足才行
max_gaps 多个interval查询在一个文档中允许的最大间距,超过最大间距的将不会被检索到;默认值是-1,即不限制,设置为0的话,所有的interval query必须彼此相连不能拆分
ordered 配置 intervals 出现的先后顺序,默认值false
filter intervals独有的过滤语法,下方有说明
  • any_of

参数 描述
intervals 一个interval集合,集合中只需满足其一即可
filter intervals独有的过滤语法,下方有说明
  • filter

在例子中我们提到filter,通过filter和intervals设定的规则可以过滤掉一些我们不想要的间隔词汇的文档,当然filter不仅仅只包含not_contaning参数
     常用的filter参数,如下:
参数 描述
containing interval query中terms之间需要包含filter中的terms
contained_by interval query中的字符串需要被包含在filter query的terms里
not_containing containing 对立面
not_contained_by (比较模糊,有心得的小伙伴可以私信我)contained_by 对立面

此处比较建议使用 containing和not_containing,而不建议使用contained_by和not_contained_by

我们更愿意在query中输入想查询的词条 在fitler中过滤。

  • script filters

如果上面filters语句不能满足你的需求,那么可以尝试一下script filter ,它提供了一个interval变量,通过start、end、gaps三个函数更加灵活的控制term在文本中的顺序与距离:
* 例如下方语句简单解释一下:

POST _search
{
  "query": {
    "intervals": {
      "content": {
        "match": {
          "query": "curry shooter",
          "filter": {
            "script": {
              "source": "interval.start >= 2 && interval.end < 5 && interval.gaps == 1"
            }
          }
        }
      }
    }
  }
}


    curry(interval.start)要出现在偏移量>=2的位置,shooter(interval.end)要出现在偏移量<5的位置 并且curry和shooter之间的间距(intercal.gaps)为1 才可以查得到    

3) JavaSDK

* 参照下方DSL编写简单Java Api调用

虽然调用方式有所不同,不过最后本质上依然是一个queryBuilder工厂铸造的对象,可以放入bool中配合其他查询一起使用!
 

            {
              "query": {
                "intervals": {
                  "content": {
                    "all_of": {
                      "max_gaps": 5,
                      "ordered": true,
                      "intervals": [
                        {
                          "match": {
                            "query": "Curry shooter",
                            "max_gaps": 1,
                            "ordered": "true",
                            "filter": {
                              "not_containing": {
                                "match": {
                                  "query": "bad"
                                }
                              }
                            }
                          }
                        }
                      ]
                    },
                    "boost": 2
                  }
                }
              }
            }
 public void customerIntervalsQuery() throws IOException {
   
        // 构建intervals数组
        List<IntervalsSourceProvider> intervalsSourceProviderList = new ArrayList<>(16);
        // 构建内层match
        IntervalsSourceProvider.IntervalFilter intervalFilter = new IntervalsSourceProvider.IntervalFilter(new IntervalsSourceProvider.Match("bad", 0, true, null, null, null), "not_containing");
        IntervalsSourceProvider.Match mainProvider = new IntervalsSourceProvider.Match("Curry shooter", gaps, true, null, intervalFilter, null);
        // 将math加入intervals[]
        intervalsSourceProviderList.add(mainProvider);



        // 最后放入all of对象中
        IntervalsSourceProvider intervalsSourceProvider = new IntervalsSourceProvider.Combine(intervalsSourceProviderList, true, 5, null);
        // all of放入最外层的intervals
        IntervalQueryBuilder intervalQueryBuilder = new IntervalQueryBuilder("content", intervalsSourceProvider);
        SearchRequest request = new SearchRequest("test_index");
        SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
        searchSourceBuilder.query(intervalQueryBuilder);
        System.out.println(searchSourceBuilder.toString());

		// 发送请求
        request.source(searchSourceBuilder);
        SearchResponse search = restHighLevelClient.search(request, RequestOptions.DEFAULT);
        SearchHits hits = search.getHits();
        System.out.println(hits);
    }

Except for the passage of time and the separation of life and death,I can do all things.

参考资料:

Intervals query | Elasticsearch Guide [7.9] | Elastic

ElasticSearch官方文档

Elasticsearch Intervals query 间隔查询_yuanxun4683的博客-程序员信息网_elasticsearch interval

作者:墨菲灬

9.2.1-elasticsearch全文检索之intervals查询_红笺小字-程序员信息网

作者:hjx

elasticsearch 7.0 新特性之Intervals query - 简书

作者:码到成功_易企秀

版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://blog.csdn.net/weixin_42484190/article/details/119941425

智能推荐

解决oracle11g的ORA-12505问题_我叫毕加索的博客-程序员信息网

今天在使用SQL Developer的时候连不上去,报ORA-12505错误,但是SQLPLUS可以连接。检查服务名,是OracleServiceORCL,那SID应当就是orcl,但是使用该SID仍然无法连接。查阅资料后解决方法如下:1.  打开数据库实例的目录(我的是C:\app\Administrator\product\11.2.0\dbhome_1\NETWORK\ADMIN)找到lis...

php-输入两个字符串,从第一字符串中删除第二个字符串中所有的字符_lotusgrm的博客-程序员信息网

这道题目是好未来的笔试题,我是在牛客上看到的,因为对于php比较熟悉所以就用php试着解决一下,但是不知道是牛客在线编译系统的问题还是其他问题,我在自己本地的编译器上可以正常运行,但是在牛客上一直显示case率是25%但是这个方法自我感觉是争取的,分享一下看看:首先题目要求是从第一个字符串中删除第二个字符串中的所有字符,这个就不禁让我们想到使用数组相减的方法,字符串和数组不分家,一

基于STM32封装的HTTP请求_PotoYoung的博客-程序员信息网_stm32 实现http

通过封装http头,向服务器发送get请求,通过get请求上传数据,并获取返回值

anaconda库安装、jupyter设置_剑宇2022的博客-程序员信息网

anaconda常用操作Anaconda 环境操作:• 首先说一点:Windows下 Anaconda Prompt 这个东西就是用来管理Anaconda的,使用的是conda这样的一种命令在Linux中,可以直接在终端中输入conda 命令• 可以使用conda命令创建新的python环境(python版本,包),新的环境与原来的环境不相关。这样,方便不同的应用中使用不同的python版本。• 创建新环境的步骤如下:1、首先在所在系统中安装Anaconda。可以打开命令行输入conda -V检

向线程传递参数的两种基本方法_weixin_30247159的博客-程序员信息网

在传统的同步开发模式下,当我们调用一个函数时,通过这个函数的参数将数据传入,并通过这个函数的返回值来返回最终的计算结果。但在多线程的异步开发模式下,数据的传递和返回和同步开发模式有很大的区别。由于线程的运行和结束是不可预料的,因此,在传递和返回数据时就无法象函数一样通过函数参数和return语句来返回数据。本文就以上原因介绍了几种用于向线程传递数据的方法。 欲先取之,必先予之。一般在使用线程时...

virtual函数和虚函数表vtable_小飞将的博客-程序员信息网

example:#include &lt;iostream&gt;class B{public: virtual void bar(); virtual void qux();};void B::bar(){ std::cout &lt;&lt; "This is B's implementation of bar" &lt;&lt; std::endl;}void B::qux(){ std::cout &lt;&lt; "This is B's implemen

随便推点

使用matplotlib制作“折线图”:pyplot.plot()/给多组数据添加解释图标/放大坐标轴部分区间_牛奶没法用的博客-程序员信息网_plt 拉伸某区间的折线

创建饼状图创建饼状图:plt.pie()参数是一个float类型的list修改倾斜角度:plt.axis(‘equal’) 添加饼状图细节项展示比例,使用plt.pie()函数,在中间添加参数:autopct(可取值:%d%%表示整数百分比;%0.1f一位小数;%0.1f%%一位小数百分比;%0.2f%%两位小数百分比)展示项目内容,两种方法:a. 直接添加在颜色...

顺序栈/链式栈_sandmm112的博客-程序员信息网_顺序栈是用顺序表的表头作 ,表尾作 ;链式栈是用单链表的表头作 ,表尾作 ;

        栈是是一种限定性的线性表,它将线性表的插入和删除限定为仅在表的一端进行。将表中允许插入和删除的一端成为栈顶。所以栈顶的位置是不断动态变化的。它具有“后进先出”的特点。因为栈是由线性表实现的,所以,栈有两种存储结构:顺序存储和链式存储。对应的栈成为顺序栈和链式栈。下面,分别来介绍这两种栈的相关操作。一,顺序栈        它与顺序表类似,即用一组地址连续的空间存放栈中的元素。之前的...

全自动驾驶汽车的技术与未来_Suresoft China的博客-程序员信息网

2015年底上市的 Genesis EQ900的高速公路驾驶辅助系统 (HAD, Highway Driving Assist System),是韩国国内最初展示的自动驾驶汽车技术,从那时候开始捷尼赛思就与全球汽车制造商竞争者一起为即将到来的自动驾驶技术商业化时代做着准备。除此以外,门户网站NAVER是韩国IT行业中最早在公共道路上试运行无人驾驶汽车的企业。然而,自动驾驶事故责任归属的法律问题、复杂的城市交通交通信号以及现有技术无法控制各类道路交通状况等问题是全自动驾驶迟迟无法实现商业化的原因,这便是需要

Ubuntu16.04安装显卡驱动方案(亲测有效)_龙啸wyh的博客-程序员信息网

1.下载驱动 :https://www.nvidia.cn/Download/Find.aspx?lang=cnBETA版过新,稳定性尚未可知,选择非beta版本的最新版驱动2.Ubuntu系统集成的显卡驱动程序是nouveau,我们需要先将nouveau从Linux内核卸载掉才能安装NVIDIA官方驱动。将nouveau添加到黑名单blacklist.conf中,(关于blacklist参见...

【数据库----MySQL】Mysql操作容量限制问题_Sunny3096的博客-程序员信息网

【问题描述】Error updating database. Cause: com.mysql.jdbc.PacketTooBigException: Packet for query is too large (1082 &gt; 1024)在做查询数据库操作时,报了以上错误,还有out of memery heap hacp ,原因是mysql的max_allowed_packet设置...

android rn 和webview,react-native中安卓webview和js层通信_骆逸的博客-程序员信息网

前言:学习rn已经有大半年了,目前的项目是采用rn的,在项目中曾遇到webview中调用postMessage,然后在浏览器和真机中查看,发现在浏览器中会报错,后者不会报错,然后觉得很奇怪,因此就去粗略的研究了一下rn中webview的实现。由于webview涉及很多东西,所以这一篇写介绍一下安卓的webview,下篇再继续介绍ios的webview。介绍:webview主要是用来进行页面请求,页...

推荐文章

热门文章

相关标签