定义和特点
一个分布式可扩展的实时搜索和分析引擎,一个建立在全文搜索引擎 Apache Lucene(TM) 基础上的搜索引擎.
主要特点|--分布式实时文件存储;
|--实时分析的分布式搜索引擎;
|--可以扩展到上百台服务器,处理PB级别的结构化或非结构化数据;
Elasticsearch的文件存储
Elasticsearch是面向文档型数据库,一条数据在这里就是一个文档,用JSON作为文档序列化的格式,比如下面这条用户数据:
{
"name" : "John",
"sex" : "Male",
"age" : 25,
"birthDate": "1990/05/01",
"about" : "I love to go rock climbing",
"interests": [ "sports", "music" ]
}
用Mysql这样的数据库存储就会容易想到建立一张User表,在Elasticsearch里这就是一个文档,
当然这个文档会属于一个User的类型,各种各样的类型存在于一个索引当中。
这里有一份简易的将Elasticsearch和关系型数据术语对照表:
|
|--关系数据库 ⇒ 数据库 ⇒ 表 ⇒ 行 ⇒ 列(Columns)
|--Elasticsearch ⇒ 索引(Index) ⇒ 类型(type) ⇒ 文档(Docments) ⇒ 字段(Fields)
一个 Elasticsearch 集群可以包含多个索引(数据库),也就是说其中包含了很多类型(表)。
这些类型中包含了很多的文档(行),然后每个文档中又包含了很多的字段(列)。
Elasticsearch的交互,可以使用Java API,也可以直接使用HTTP的Restful API方式,
比如我们打算插入一条记录,可以简单发送一个HTTP的请求:
|
|--PUT /megacorp/employee/1
| {
| "name" : "John",
| "sex" : "Male",
| "age" : 25,
| "about" : "I love to go rock climbing",
| "interests": [ "sports", "music" ]
| }
倒排索引
为了提高搜索的性能,难免会牺牲某些其他方面,比如插入/更新。
前面看到往Elasticsearch里插入一条记录,其实就是直接PUT一个json的对象,这个对象有多个fields,
那么在插入这些数据到Elasticsearch的同时,Elasticsearch还默默1的为这些字段建立索引--倒排索引,
因为Elasticsearch最核心功能是搜索。
假设有这么几条数据
| ID | Name | Age | Sex |
| -- |------|-----| -------|
| 1 | Kate | 24 | Female |
| 2 | John | 24 | Male |
| 3 | Bill | 29 | Male |
ID是Elasticsearch自建的文档id,那么Elasticsearch建立的索引如下:
Name:
| Term | Posting List |
| ---- | ------------ |
| Kate | 1 |
| John | 2 |
| Bill | 3 |
Age:
| Term | Posting List |
| ---- | ------------ |
| 24 | [1,2] |
| 29 | 3 | |
Sex:
| Term | Posting List |
| ------ | ------------ |
| Female | 1 |
| Male | [2,3] |
Posting List
Elasticsearch分别为每个field都建立了一个倒排索引,Kate, John, 24, Female这些叫term,而[1,2]就是Posting List。
Posting list就是一个int的数组(底层会使用Roaring bitmap 进行压缩),存储了所有符合某个term的文档id。
Elasticsearch使用规范
|
|--不需要索引的字段,一定要明确定义出来,因为默认是自动建索引的
|--同样的道理,对于String类型的字段,不需要analysis的也需要明确定义出来,因为默认也是会analysis的
|--选择有规律的ID很重要,随机性太大的ID(比如java的UUID)不利于查询