为什么使用ES? 【参考下面】转
https://blog.csdn.net/laoyang360/article/details/52244917
ES=elaticsearch简写, Elasticsearch是一个开源的高扩展的分布式全文检索引擎,它可以近乎实时的存储、检索数据;本身扩展性很好,可以扩展到上百台服务器,处理PB级别的数据。
Elasticsearch也使用Java开发并使用Lucene作为其核心来实现所有索引和搜索的功能,但是它的目的是通过简单的RESTful API来隐藏Lucene的复杂性,从而让全文搜索变得简单。
1)Lucene只是一个库。想要使用它,你必须使用Java来作为开发语言并将其直接集成到你的应用中,更糟糕的是,Lucene非常复杂,你需要深入了解检索的相关知识来理解它是如何工作的。
1.3 ES主要解决问题:
1)检索相关数据;
2)返回统计结果;
3)速度要快。
1) 2013年初,GitHub抛弃了Solr,采取ElasticSearch 来做PB级的搜索。 “GitHub使用ElasticSearch搜索20TB的数据,包括13亿文件和1300亿行代码”。
实际项目开发实战中,几乎每个系统都会有一个搜索的功能,当搜索做到一定程度时,维护和扩展起来难度就会慢慢变大,所以很多公司都会把搜索单独独立出一个模块,用ElasticSearch等来实现。
近年ElasticSearch发展迅猛,已经超越了其最初的纯搜索引擎的角色,现在已经增加了数据聚合分析(aggregation)和可视化的特性,如果你有数百万的文档需要通过关键词进行定位时,ElasticSearch肯定是最佳选择。当然,如果你的文档是JSON的,你也可以把ElasticSearch当作一种“NoSQL数据库”, 应用ElasticSearch数据聚合分析(aggregation)的特性,针对数据进行多维度的分析。
必要的Head、kibana、IK(中文分词)、graph等插件的详细安装和使用。
http://blog.csdn.net/column/details/deep-elasticsearch.html
http://www.ibm.com/developerworks/library/j-use-elasticsearch-java-apps/index.html
1)国外:https://discuss.elastic.co/
2)国内:http://elasticsearch.cn/
https://blog.csdn.net/laoyang360/article/details/51931981
Mysql与Elasticsearch核心概念对比示意图
以上表为依据,
ES中的新建文档(在Index/type下)相当于Mysql中(在某Database的Table)下插入一行数据。
1、新建文档(类似mysql insert插入操作) http://localhost:9200/blog/ariticle/1 put
即相当于在ES服务器上的index数据库上创建了type表,并对其进行增删等操作。
https://blog.csdn.net/laoyang360/article/details/73368740
参考这个: 16、Elasticsearch检索分类深入详解—基础篇
Elasticsearch中当我们设置Mapping(分词器、字段类型)完毕后,就可以按照设定的方式导入数据。
有了数据后,我们就需要对数据进行检索操作。根据实际开发需要,往往我们需要支持包含但不限于以下类型的检索:
1)精确匹配,类似mysql中的 “=”操作;
2)模糊匹配,类似mysql中的”like %关键词% “查询操作;
3)前缀匹配;
4)通配符匹配;
5)正则表达式匹配;
6)跨索引匹配;
7)提升精读匹配。
细数一下,我们的痛点在于:
1)ES究竟支持哪些检索操作?
2)如何实现ES精确值检索、指定索引检索、全文检索?
检索子句的行为取决于查询应用于过滤(filter)上下文还是查询/分析(query)上下文。【在DSL预语法中主要体现在filter和match】
对比如下:
过滤上下文——对应于结构化检索
01.核心回答的问题是:“这个文档是否符合这个查询条款?” 02.答案是简单的是或否,不计算分数 03.过滤器上下文主要用于过滤结构化数据。类似于Mysql中判定某个字段是否存在: |
分析上下文——对应于全文检索
1)核心回答了“本文档与此查询子句是否匹配?”的问题。 2)除了决定文档是否匹配之外,查询子句还会计算一个_score,表示文档与其他文档的匹配程度。 综合应用场景如下: |
这里发现有个公益项目的es应该考虑使用过滤上下文,而不是查询上下文,因为搜索框只是搜索过滤而不考虑计算分值。
注:原链接作者:3-7根据我随着我开发深入再做更新。
针对字段类型: 日期、时间、数字类型,以及精确的文本匹配。
结构化检索特点:
* 1)结构化查询,我们得到的结果 总是 非是即否,要么存于集合之中,要么存在集合之外。
* 2)结构化查询不关心文件的相关度或评分;它简单的对文档包括或排除处理。
当进行精确值查找时, 我们会使用过滤器(filters)。过滤器很重要,因为它们执行速度非常快,不会计算相关度(直接跳过了整个评分阶段)而且很容易被缓存。如下: 使用 constant_score 查询以非评分模式来执行 term 查询并以一作为统一评分。
精确值java api jest使用方法:
searchSourceBuilder.query(QueryBuilders.termQuery(“text.keyword”, “来自新华社的报道”));
对应查询的 DSL写法 可以直接参考原链接,或者官网,或者百度。
高级全文查询通常用于在全文本字段(如电子邮件正文)上运行全文查询。他们了解如何对被查询的字段进行分析,并在执行前将每个字段的分析器(或search_analyzer)应用于查询字符串。
2.1 匹配检索(match query) 2.2 匹配解析检索 match_phrase query 2.3 匹配解析前缀检索(match_phrase_prefix) 2.4 多字段匹配检索( multi_match query) 2.5 字符串检索(query_string) 2.6 简化字符串检索(simple_query_string) |
有两种方式可以执行全文检索:
1)URL检索方式 (使用包含参数的检索API,参数作为URL的一部分)。如:GET /bookdb_index/book/_search?q=guide
2)使用完整的ES DSL,其中Json body作为请求体。 其执行结果如方式1)结果一致。
【full body的DSL为您提供了创建更复杂查询的更多灵活性(我们将在后面看到)以及指定您希望的返回结果。
如:结果数的表示方式:size;
偏移值的表示方式:from;
指定返回字段 的表示方式 :_source;
高亮显示 的表示方式 :highliaght。】
【https://blog.csdn.net/laoyang360/article/details/79249823】
问题:某个词组在Elasitcsearch中的某个document中存在,就一定通过某种匹配方式把它搜出来。
举例:title=公路局正在治理解放大道路面积水问题。
输入关键词:道路,能否搜索到这个document呢?
实际应用中可能需要:
1)检索关键词”理解”、”解放”、”道路”、“理解放大”,都能搜出这篇文档。
2)单个的字拆分“治”、“水”太多干扰,不要被检索出来。 【即,单个字不检索】
3)待检索的词不在词典中,也必须要查到。 【词典,即分词】
4)待检索词只要在原文title或content中出现,都要检索到。
5)检索要快,要摒弃wildcard模糊匹配性能问题。
常用的stand标准分词,可以满足要求 1)、3)、4)、5)。
标准分词器是什么鬼?
标准分析仪是默认分析仪,如果没有指定,则默认使用该分词器。
它提供了基于语法的标记,并且适用于大多数语言。 对于中文字符串,会逐个汉字分词。
标准分词器的结果如下:
GET /ik_index/_analyze?analyzer=standard
{
"text":"公路局正在治理解放大道路面积水问题"
}
返回: 公,路,局,正,在,治,理,解,放,大,道,路,面,积,水,问,题
但,标准分词器会出现冗余数据非常多。
针对要求2),排除match检索,排除stand分词。 【 2) 要求单个字不检索】
针对要求5),排除wildcard模糊检索。 【 5)检索要快。】
针对要求3)、4),新词也要被检索到比如:“声临其境”、“孙大剩”等也要能被搜索到。 【3)检索词 不在词典中】
针对要求1),采用match_phrase貌似靠谱些。【匹配到关键字 都能搜出这篇文档】
使用IK-max-word细粒度分词器,结合match_phrase试一试?
举例:
数据:"title":"公路局正在治理解放大道路面积水问题";
搜索:"title.ik_my_max":"道路";
结果:无结果返回。
分析:
细粒度ik_max_word分词结果为 :
公路局 ,公路 ,路局 ,路 ,局正 ,正在 ,正 ,治理 ,治 ,理解 ,
理 ,解放 ,解 , 放大 ,大道 ,大 ,道路 ,道 ,路面 ,路 ,
面积 ,面 ,积水 ,积 ,水 ,问题
检索的时候,道路拆分为: 道路0 道1 路2
match_phrase检索时,文档必须同时满足以下两个条件,才能被检索到:
1)分词后所有词项都出现在该字段中;
2)字段中的词项顺序要一致。 【该点未满足(中间多了一个 路面),所以没搜索到】
如果是 "title":"党员干部坚持走马克思主义道路的重要性" ; 搜索 道路 是可以匹配到的。
【分词: 主义, 道路, 道, 路, 重要性,】
有的;和match_pharse类似,不过match_phrase_prefix支持最后一个term前缀匹配。
我们自己开发搜索引擎的时候,经常会出现基于title或者content字段进行检索。
如果用match检索,会出现噪音很多的情况;
如果用match_phrase,会出现某些字段检索不出来的情况,如上分析的“道路”;
如果用wildcard,能检索出来,但又有性能问题的存在。
这时候,可以考虑下: match_phrase_prefix。