部分匹配(Partial Matching)

敏锐的读者可能已经发现到眼下为止,介绍的查询都是在整个词条层面进行操作的。

匹配的最小单元必须是一个词条。你仅仅能找到存在于倒排索引(Inverted Index)中的词条。

可是假设你想匹配词条的一部分,而不是整个词条呢?部分匹配(Partial Matching)同意用户指定词条的一部分然后找到含有该部分的不论什么单词。

匹配词条一部分这一需求在全文搜索引擎领域比你想象的要不那么常见。假设你有SQL的背景。你可能有过使用以下的SQL语句来实现一个简单的全文搜索功能的经历:

WHERE text LIKE "*quick*"
AND text LIKE "*brown*"
AND text LIKE "*fox*"

当然,通过ES我们能够借助分析过程(Analysis Process)和倒排索引来避免这样的"蛮力"技术。

为了同一时候匹配"fox"和"foxes",我们能够简单地使用一个词干提取器,然后将词干进行索引。这样就没有必要进行部分匹配了。

即便如此,在某些场合下部分匹配还是有作用的。常见的用例比方:

  • 匹配邮政编码,产品序列号。或者其他以某个特定前缀开头的或者可以匹配通配符甚至正則表達式的not_analyzed值。
  • 即时搜索(Search-as-you-type) - 在用户完毕搜索词条的输入前就展示最有可能的结果。

  • 匹配德语或者荷兰语这一类语言,它们韩哟长复合单词。比方Weltgesundheitsorganisation(World Health Organization)。

我们以针对精确值not_analyzed字段的前缀匹配開始。介绍部分匹配的技术。

邮政编码和结构化数据

我们以英国的邮政编码来说明怎样在结构化数据上使用部分匹配。

英国邮政编码是一个定义清晰的结构。比方,W1V 3DG这个邮政编码能够被分解成下面几个部分:

  • W1V:这个部分表明了邮政地域和地区(Postal Area and District):

    • W 表明了地域(Area)。使用一个或者两个字母。
    • 1V 表明了地区(District)。使用一个或者两个数字,可能尾随一个字母。
  • 3DG:该部分表明了街道或者建筑:
    • 3 表明了区域(Sector)。使用一个数字。

    • DG 表明了单元,使用两个字母。

如果我们将邮政编码索引为精确值的not_analyzed字段,因此我们能够创建例如以下索引:

PUT /my_index
{
"mappings": {
"address": {
"properties": {
"postcode": {
"type": "string",
"index": "not_analyzed"
}
}
}
}
}

然后索引一些邮政编码:

PUT /my_index/address/1
{ "postcode": "W1V 3DG" } PUT /my_index/address/2
{ "postcode": "W2F 8HW" } PUT /my_index/address/3
{ "postcode": "W1F 7HW" } PUT /my_index/address/4
{ "postcode": "WC1N 1LZ" } PUT /my_index/address/5
{ "postcode": "SW5 0BE" }

如今我们的数据就准备就绪了。

前缀查询(Prefix Query)

我们能够通过一个简单的prefix查询来得到全部以W1开头的邮政编码:

GET /my_index/address/_search
{
"query": {
"prefix": {
"postcode": "W1"
}
}
}

prefix查询是一个工作在词条级别的低级查询。它不会在搜索前对查询字符串进行解析。它如果用户会传入一个须要查询的精确前缀。

TIP

默认情况下。prefix查询不会计算相关度分值。它仅仅是进行文档匹配,匹配的文档的分值为1。

事实上,相比查询它更像一个过滤器。

prefix查询和prefix过滤器的唯一差别在于过滤器能够被缓存。

之前。我们提到过"你仅仅能找到存在于倒排索引中的词条"。可是对于这些邮政编码我们并没有进行不论什么特殊处理;每一个邮政编码仅仅是被当做精确值被简单地索引。那么prefix查询是怎样工作的呢?

记住倒排索引是由唯一词条得有序列表构成的(此种情况下。即邮政编码)。对于每一个词条。它会列举全部含有该词条的文档ID。对于我们的演示样例文档,倒排索引例如以下所看到的:

Term:          Doc IDs:
-------------------------
"SW5 0BE" | 5
"W1F 7HW" | 3
"W1V 3DG" | 1
"W2F 8HW" | 2
"WC1N 1LZ" | 4
-------------------------

为了支持前缀匹配。查询会运行下面的步骤:

  1. 遍历词条列表并找到以W1开头的词条。

  2. 收集相应的文档ID。
  3. 移动到下一个词条。

  4. 假设该词条也以W1开头。那么反复步骤2;否则结束操作。

虽然以上的步骤对于我们的小样例而言能非常好地工作,想象一下当倒排索引含有一百万个以W1开头的邮政编码时的情景,prefix查询须要訪问一百万个词条来得到结果。

而前缀越短,就意味着须要訪问越多的词条。

假设我们查询前缀为W,而不是W1的词条。可能会匹配多达一千万个词条。

注意

prefix查询和过滤器对于即时(Ad-hoc)的前缀匹配是实用处的,可是在使用它们的时候须要小心。

对于拥有少量词条的字段能够任意地使用。可是它们的扩展性较差,可能会让你的集群承受过多的压力。

能够通过使用一个较长的前缀来限制它们对于集群的影响。这能够降低须要訪问的词条的数量。

在本章的后面部分,我们将推出一个解决方案,使指数在更有效的前缀匹配。但首先,让我们来看看两个相关查询:wildcard以及regexp询。

[Elasticsearch] 部分匹配 (一) - 前缀查询的更多相关文章

  1. [Elasticsearch] 部分匹配 (三) - 查询期间的即时搜索

    本章翻译自Elasticsearch官方指南的Partial Matching一章. 查询期间的即时搜索(Query-time Search-as-you-type) 如今让我们来看看前缀匹配可以怎样 ...

  2. java操作elasticsearch实现前缀查询、wildcard、fuzzy模糊查询、ids查询

    1.前缀查询(prefix) //prefix前缀查询 @Test public void test15() throws UnknownHostException { //1.指定es集群 clus ...

  3. [Elasticsearch] 邻近匹配 (三) - 性能,关联单词查询以及Shingles

    提高性能 短语和邻近度查询比简单的match查询在性能上更昂贵.match查询仅仅是查看词条是否存在于倒排索引(Inverted Index)中,而match_phrase查询则须要计算和比較多个可能 ...

  4. [ElasticSearch]Java API 之 词条查询(Term Level Query)

    1. 词条查询(Term Query)  词条查询是ElasticSearch的一个简单查询.它仅匹配在给定字段中含有该词条的文档,而且是确切的.未经分析的词条.term 查询 会查找我们设定的准确值 ...

  5. [Elasticsearch] 部分匹配 (四) - 索引期间优化ngrams及索引期间的即时搜索

    本章翻译自Elasticsearch官方指南的Partial Matching一章. 索引期间的优化(Index-time Optimizations) 眼下我们讨论的全部方案都是在查询期间的.它们不 ...

  6. [Elasticsearch] 邻近匹配 (一) - 短语匹配以及slop參数

    本文翻译自Elasticsearch官方指南的Proximity Matching一章. 邻近匹配(Proximity Matching) 使用了TF/IDF的标准全文搜索将文档,或者至少文档中的每一 ...

  7. ElasticSearch 学习记录之ES查询添加排序字段和使用missing或existing字段查询

    ES添加排序 在默认的情况下,ES 是根据文档的得分score来进行文档额排序的.但是自己可以根据自己的针对一些字段进行排序.就像下面的查询脚本一样.下面的这个查询是根据productid这个值进行排 ...

  8. 第三百六十六节,Python分布式爬虫打造搜索引擎Scrapy精讲—elasticsearch(搜索引擎)的bool组合查询

    第三百六十六节,Python分布式爬虫打造搜索引擎Scrapy精讲—elasticsearch(搜索引擎)的bool组合查询 bool查询说明 filter:[],字段的过滤,不参与打分must:[] ...

  9. 四十五 Python分布式爬虫打造搜索引擎Scrapy精讲—elasticsearch(搜索引擎)的bool组合查询

    bool查询说明 filter:[],字段的过滤,不参与打分must:[],如果有多个查询,都必须满足[并且]should:[],如果有多个查询,满足一个或者多个都匹配[或者]must_not:[], ...

随机推荐

  1. android应用开发--------------看RadioGroup源代码,写相似单选选项卡的集成控件(如底部导航,tab等等)

    博客为 有时个哥 原创.如需转载请标明出处:http://blog.csdn.net/ls703/article/details/46694967 watermark/2/text/aHR0cDovL ...

  2. Android源码及SDK国内镜像下载

    Android源码及SDK国内镜像下载Android源码下载: 今天发现,清华大学提供AOSP镜像,以前都是从Google的站点下载同步更新的,但是现在有了国内的镜像站点就好多了,下载Androidd ...

  3. 重新想象 Windows 8 Store Apps (29) - 图片处理

    原文:重新想象 Windows 8 Store Apps (29) - 图片处理 [源码下载] 重新想象 Windows 8 Store Apps (29) - 图片处理 作者:webabcd介绍重新 ...

  4. 【原创】编写多线程Python爬虫来过滤八戒网上的发布任务

    目标: 以特定语言技术为关键字,爬取八戒网中网站设计开发栏目下发布的任务相关信息 需求: 用户通过设置自己感兴趣的关键字或正则表达式,来过滤信息. 我自己选择的是通过特定语言技术作为关键字,php.j ...

  5. CSS设计指南之理解盒子模型

    原文:CSS设计指南之理解盒子模型 一.理解盒模型 每一个元素都会在页面上生成一个盒子.因此,HTML页面实际上是由一堆盒子组成的.默认情况下,每个盒子的边框不可见,背景也是透明的,所以我们不能直接看 ...

  6. Cocos2d-x3.0游戏实例《不要救我》三——背景滚动周期

    好.让我们来解释一下这个无限循环滚动的背景.这方面的知识一直讲到烂.我以前的文章还介绍了.所以不是那么特别清楚. 笨木头花心贡献,啥?花心?不呢,是用心~ 转载请注明,原文地址:http://www. ...

  7. [LeetCode119]Pascal's Triangle II

    题目: Given an index k, return the kth row of the Pascal's triangle. For example, given k = 3,Return [ ...

  8. IT忍者神龟之使用 PowerDesigner

    1. 启动 PowerDesigner 新建物理数据模型 watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvdmlweWhk/font/5a6L5L2T/fon ...

  9. 条形码/二维码之开源利器ZXing图文介绍(转)

    继前面介绍的一个日本开源软件(该软件只能实现QRCode)原文: Java实现二维码QRCode的编码和解码(http://sjsky.iteye.com/blog/1136934 ),今发现又一优秀 ...

  10. 什么时候PHP经验MySQL存储过程

    1.MySQL存储过程 数据库语言,我们经常使用的操作SQL语句必须首先编译在运行时.然后运行,存储过程(Stored Procedure)它被设置为完成一个特定的功能SQL报表设置.编译存储在数据库 ...