索引设计的几个常用算法

合集下载
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

索引设计的⼏个常⽤算法
B+、B- Tree(mysql,oracle,mongodb)
主要⽤在关系数据库的索引中,如oracle,mysql innodb;mongodb中的索引也是B-树实现的;还有HBase中HFile中的DataBlock的索引等等。

动态查找树主要有:⼆叉查找树(Binary Search Tree),平衡⼆叉查找树(Balanced Binary Search Tree),红⿊树(Red-Black Tree ),B-tree/B+-tree/ B*-tree (B~Tree)。

前三者是典型的⼆叉查找树结构,其查找的时间复杂度O(log2N)与树的深度相关,那么降低树的深度⾃然会提⾼查找效率。

但是咱们有⾯对这样⼀个实际问题:就是⼤规模数据存储中,实现索引查询这样⼀个实际背景下,树节点存储的元素数量是有限的(如果元素数量⾮常多的话,查找就退化成节点内部的线性查找了),这样导致⼆叉查找树结构由于树的深度过⼤⽽造成磁盘I/O读写过于频繁,进⽽导致查询效率低下,那么如何减少树的深度(当然是不能减少查询的数据量),⼀个基本的想法就是:采⽤多叉树结构(由于树节点元素数量是有限的,⾃然该节点的⼦树数量也就是有限的)。

也就是说,因为磁盘的操作费时费资源,如果过于频繁的多次查找势必效率低下。

那么如何提⾼效率,即如何避免磁盘过于频繁的多次查找呢?根据磁盘查找存取的次数往往由树的⾼度所决定,所以,只要我们通过某种较好的树结构减少树的结构尽量减少树的⾼度,那么是不是便能有效减少磁盘查找存取的次数呢?那这种有效的树结构是⼀种怎样的树呢?
这样我们就提出了⼀个新的查找树结构——多路查找树。

根据平衡⼆叉树的启发,⾃然就想到平衡多路查找树结构,也就是B-tree,即B树结构,B树的各种操作能使B树保持较低的⾼度,从⽽达到有效避免磁盘过于频繁的查找存取操作,从⽽有效提⾼查找效率。

Hash表+桶(redis)
mysql中的adaptive hash index,redis中的数据存储实现都是采⽤hash,可以⾼效的进⾏数据的查询。

哈希表(Hash table,也叫散列表),是根据关键码值(Key value)⽽直接进⾏访问的数据结构。

也就是说,它通过把关键码值映射到表中⼀个位置来访问记录,以加快查找的速度。

这个映射函数叫做散列函数,存放记录的数组叫做散列表。

哈希表的做法其实很简单,就是把Key通过⼀个固定的算法函数既所谓的哈希函数转换成⼀个整型数字,然后就将该数字对数组长度进⾏取余,取余结果就当作数组的下标,将value存储在以该数字为下标的数组空间⾥。

⽽当使⽤哈希表进⾏查询的时候,就是再次使⽤哈希函数将key转换为对应的数组下标,并定位到该空间获取value,如此⼀来,就可以充分利⽤到数组的定位性能进⾏数据定位
数组的特点是:寻址容易,插⼊和删除困难;⽽链表的特点是:寻址困难,插⼊和删除容易。

综合两者特性,设计⼀种寻址容易,插⼊删除也容易的数据结构,如拉链法实现的哈希表。

Booleam Filter(HBase)
HBase中的rowkey设置建⽴Booleam Filter映射,⽤于快速判断rowkey是否在⼀个HFile中。

在分布式数据库中⽤的⽐较多。

基于BitMap的存储结构,采⽤的是哈希函数的⽅法,将⼀个元素映射到⼀个 m 长度的阵列上的⼀个点,当这个点是 1 时,那么这个元素在集合内,反之则不在集合内。

这个⽅法的缺点就是当检测的元素量很多时候可能有冲突,解决⽅法就是使⽤ k 个哈希函数对应 k 个点,如果所有点都是 1 的话,那么元素在集合内,如果有 0 的话,元素则不再集合内。

相关文档
最新文档