正排索引

简介: 介绍ElasticSearch相关正排索引

1. 正排索引

正排索引: 正排索引是指文档ID为key,表中记录每个关键词出现的次数,查找时扫描表中的每个文档中字的信息,直到找到所有包含查询关键字的文档。

网页A中的内容片段:  

Tom is a boy.     Tom is a student too.

正排索引如下:

内容 Tom is a boy Tom is a student too
分词 Tom is a boy student too
  • 正排索引
Index Word word_hit(词出现的次数) word_offset(词出现的位置)
TA Tom 2 1,5
is 2 2,6
a 2 3,7
boy 1 4
student 1 8
too 1 9

出现的位置进行差分序列

Index word word_hit(词出现的次数) word_offset(词出现的位置)
docid Tom 2 1,4
is 2 2,4
a 2 3,4
boy 1 4
student 1 8
too 1 9
  • 根据位置还原字符串
1 2 3 4 5 6 7 8 9
Tom Tom
is is
a a
boy
student
too

从上面的介绍可以看出,正排是以 docid 作为索引的,但是在搜索的时候我们基本上都是用关键词来搜索。


所以,试想一下,我们搜一个关键字(Tom),当100个网页的10个网页含有Tom这个关键字。但是由于是正排是doc id 作为索引的,所以我们不得不把100个网页都扫描一遍,然后找出其中含有Tom的10个网页。然后再进行rank,sort等。效率就比较低了。尤其当现在网络上的网页数已经远远超过亿这个数量后,这种方式现在并不适合作为搜索的依赖。


不过与之相比的是,正排这种模式容易维护。由于是采用doc 作为key来存储的,所以新增网页的时候,只要在末尾新增一个key,然后把词、词出现的频率和位置信息分析完成后就可以使用了。 所有正排的优点是:易维护;缺点是搜索的耗时太长;

2. 生成时间

正排索引在PUT/POST操作的时候就会生成。

3.核心原理

正排索引,也会写入磁盘文件中,然后会进入os cache中进行缓存,以提升正排索引的性能。如果os cache内存大小不足够放得下整个正排索引,就会将正排索引的数据写入磁盘文件中去。

4. 性能问题

ES官方建议,ES是大量基于os cache来进行缓存和提升性能的,不建议使用jvm内存来进行缓存,那样会导致一定的GC开销和OOM问题,所以应该给jvm更少的内存,给os cache更大的内存,这样可以大容量的os cache可以提升doc value和倒排索引的缓存和查询效率。 一般64G内存的服务器的,最多给jvm16G内存,将剩余的几十G都给os cache。

5. 存储压缩

正排索引的value在保存之前会做相应的处理,然后再来保存进去正排索引,以节省空间。具体策略如下:

(1)所有值相同,直接保留单值。

(2)少于256个值,使用table encoding模式的压缩方式处理。

(3)大于256个值,看有没有最大公约数,有就除以最大公约数,然后保留这个最大公约数和商。

(4)如果没有最大公约数,采取offset节后压缩的方式。

6. 禁用

如果的确不需要doc value,比如聚合等操作,那么可以禁用,减少磁盘空间占用。

{
  "mappings": {
    "my_type": {
      "properties": {
        "my_field": {
          "type":       "keyword"
          "doc_values": false 
        }
      }
    }
  }
}

7. 使用

聚合分析使用了倒排索引+正排索引(doc value)。

只使用倒排索引存在的问题:

如存在数据如下:

id province latency timestamp
1 江苏 68 2016-10-28
2 江苏 76 2016-10-29
3 江苏 83 2016-10-29
4 新疆 654 2016-10-28
5 江苏 105 2016-10-29
6 新疆 101 2016-10-28
7 新疆 302 2016-10-29
8 江苏 76 2016-10-28

进行如下聚合分析: 查询province为江苏的所有latency的分组数量。查询参数如下:

{
  "size":0,
  "query": {
    "match": {
      "province": "江苏"
    }
  },
  "aggs": {
    "group_by_province": {
      "terms": {
        "field": "latency"
      }
    }
  }
}

如果只使用倒排索引进行查询,则查找过程如下: 江苏 -> 1,2,3,5,8 新疆 -> 4,6,7


第一步:根据倒排索引province字段查询,得到了其对应的文档为1,2,3,5,8。


第二步:根据latency字段的值进行分组。但是这时候我们只知道我们要找的文档为1,2,3,5,8。但是文档1,2,3,5,8当中有哪些latency,我们是无法得到的。此时只能扫描整个倒排索引,根据latency的值获取到对应的文档,看本文档是否在1,2,3,5,8之中,

使用倒排索引+正排索引 首先使用倒排索引进行查询,则查找过程如下: 江苏 -> 1,2,3,5,8 新疆 -> 4,6,7

第一步:根据倒排索引province字段查询,得到了其对应的文档为1,2,3,5,8。

正排索引如下: doc1 ->江苏 68 2016-10-28 doc2 ->江苏 76 2016-10-29 ...... 这时候


第二步就不需要扫描整个倒排索引,直接使用正排索引,在文档1,2,3,5,8之中查询统计即可。

相关文章
|
存储 自然语言处理 算法
ES高频面试问题:一张图带你读懂 Elasticsearch 中“正排索引(正向索引)”和“倒排索引(反向索引)”区别
ES高频面试问题:一张图带你读懂 Elasticsearch 中“正排索引(正向索引)”和“倒排索引(反向索引)”区别
ES高频面试问题:一张图带你读懂 Elasticsearch 中“正排索引(正向索引)”和“倒排索引(反向索引)”区别
|
存储 缓存 Linux
基于dpdk的用户态协议栈设计实现(二)
基于dpdk的用户态协议栈设计实现(二)
236 0
|
存储 缓存 NoSQL
MySQL索引详解(一文搞懂)
索引是对数据库表中一列或多列的值进行排序的一种结构,使用索引可快速访问数据库表中的特定信息。
49579 17
MySQL索引详解(一文搞懂)
|
SQL 分布式计算 Java
GraalVM在Facebook大量使用,性能提升显著!
GraalVM在Facebook大量使用,性能提升显著!
896 0
GraalVM在Facebook大量使用,性能提升显著!
|
分布式数据库 索引 缓存
Elasticsearch写入原理深入详解
ES将数据存储于一个或多个索引中,索引是具有类似特性的文档的集合。类比传统的关系型数据库领域来说,索引相当于SQL中的一个数据库,或者一个数据存储方案(schema)。索引由其名称(必须为全小写字符)进行标识,并通过引用此名称完成文档的创建、搜索、更新及删除操作。
4445 0
|
存储 缓存 算法
Flink RocksDB 状态后端参数调优实践
RocksDB 的配置也是极为复杂的,可调整的参数多达百个,没有放之四海而皆准的优化方案。如果仅考虑 Flink 状态存储这一方面,我们仍然可以总结出一些相对普适的优化思路。本文先介绍一些基础知识,再列举方法。
Flink RocksDB 状态后端参数调优实践
|
11月前
|
TensorFlow 算法框架/工具 Swift
魔搭的notebook再次打开时swift导入失败
每次重新打开Notebook时,系统会显示一系列警告和错误信息。主要问题是当前安装的Keras版本为Keras 3,而Transformers库尚不支持该版本。解决方法是安装与Transformers兼容的`tf-keras`包,命令为`pip install tf-keras`,但pip后仍然报错
|
API UED 开发者
Vaadin路由魔法:导航之舟,带你穿越页面迷宫!驾驭神奇URL,解锁无限可能!
【8月更文挑战第31天】Vaadin是一款现代Java Web开发框架,其路由机制结合前后端路由,确保流畅的用户体验和高效服务器资源利用。通过`@Route`注解和`Router`类,开发者可以轻松定义和管理页面路径。例如,`@Route("home")`可指定视图路径,而参数化路由如`@Route("user/:userId")`则允许URL传参。此外,Vaadin还提供了丰富的导航API和自定义路由事件监听器,助力开发者构建结构清晰且体验优秀的Web应用。
204 0
|
缓存 TensorFlow 算法框架/工具
JAX 中文文档(十三)(3)
JAX 中文文档(十三)
336 1
|
JSON 自然语言处理 Java
性能飙升20倍!!! 超高性能协议框架fury完爆protostuff
性能飙升20倍!!! 超高性能协议框架fury完爆protostuff
425 0