热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

Indexes:RDBMSvsCoherencevsLucene

大家都熟悉SQL数据库中索引的概念.但除了关系数据库,索引被广泛应用于更多的领域.包括很多专有的产品,例如搜索引擎.搜索引擎会用到索引来划分数据.本文将在三种不同技术中索引的功能和

大家都熟悉SQL数据库中索引的概念. 但除了关系数据库, 索引被广泛应用于更多的领域. 包括很多专有的产品,例如搜索引擎. 搜索引擎会用到索引来划分数据. 本文将在三种不同技术中索引的功能和性能方面给出一个大概的比较. 这三种技术分别为: SQL数据库, 内存网格(Oracle Coherence)和全文检索引擎(Apache Lucene)

多条件查询

当面对大量数据时我们经常需要根据一些条件选出子集来. 例如股票交易或者网上交易记录. 一个简单的例子,找出所有26码的女鞋. SQL语句类似:

select * from product where type=’shoes’, color=’red’, size=’26’, gender=’W’

下面我们用这个查询来比较不同技术实现.

倒排索引

相信大家都熟悉到排索引, 不过这里还是简单的解释下. 到排索引背后的概念很简单, 也被运用在本文介绍的三种技术中.想像我们有条记录包括了A,B,C三个字段. 我们想这样的查询”select * from records where A=x”. 为了避免全表扫描,我们会创建额外的结构(索引)来记录A字段每个值所对应的所有记录.


所以如果我们需要A=1的所有记录, 只需要在A索引中找到1记录, 就会得到符合条件的所有记录列表. 看起来很简单,但理想是天使,细节是恶魔. 如何来存储索引? 如何处理多条件查询? 不同技术有不同的答案,而这些答案对查询性能有巨大的影响.

RDBMS – 基于BTree的倒排索引

BTree是在关心数据库中倒排索引最普遍的实现(也许有其他的实现但我们这次先只关注BTrees). BTree适用于磁盘存储,已经在关系数据库中应用了几十年. 典型的SQL数据库容许你在一个或多个字段上创建索引, 一张表可以创建多个索引. 如果要创建在多个字段上创建复合索引, 字段的顺序很重要.

正常情况下关系数据库在查询时只用到某表的一个BTree索引. 这是很关键的一点!

那么关系数据库如何处理上面那个关于鞋的查询呢? 数据库必须选择一个最佳索引(通常是根据统计). 数据库会用这个索引来选出查询结果的超集,然后用剩下的查询条件来过滤这个超集. 例如数据库可能选择颜色字段来作为最佳索引, 然后会用这个索引查出所有红色的产品, 接下来再在此结果上筛去不是26码的男鞋. 也就是说及时用到索引数据库仍然还有很多工作要做. 事实上这个例子对于数据库来说是个很低效的. 无论数据库选择那个单独字段作索引,都极有可能需要检查上千条记录才能完成查询.不过还是比全表扫描要好些.

有没有可能多条件查询时更有效的使用索引呢? 答案当然是肯定的.

我们可以创建符合索引, 例如尺寸和颜色. 使用这样的索引数据库就能仅仅扫描所有红色,尺寸为26码的产品. 这样我们只需要扫描少量的结果. 我们可以在数据库里调整索引来满足我们特定的查询. 但是上面这个复合索引对于其它查询,例如另外一个尺寸的红色女鞋是没有效果的.

更新: 尽管BTree索引在关系数据库中被广泛使用,但他们不是唯一的选择. 一些数据库,例如Oracle,可以使用位图索引(类似Lucence,详见下文). Oracle也能做BTree索引交集操作(类似Coherence),尽管查询分析器很少采用这个策略.

内存网格中的索引

内存网格数据也可以使用索引来提高查询的性能. 网格通常采用内存数据结构(哈希表或排序树),而不是BTree. 以Oracle Coherence为例. 在Coherence中(包括一般的数据网格)数据是分布在多个集群节点上(processes participating in grid), 每个对象都有自己的节点. 索引可是跨节点分布的;每个节点负责自己节点上数据的索引.

当在Coherence上查询, 查询会被广播到所用节点上,每个节点在自己本地数据上执行查询操作,然后返回结果集. 所有节点的结果集最后被合并成最后的查询结果.

每个节点只存储所有数据的一部分,而所有这些数据都在内存中而不是磁盘上. 所以和关系数据相比,网格采用稍微不同的方法来使用索引. 不像关系数据库, Coheren能用多个索引来执行一个简单的查询.

回到最初的例子上. 假设我们在不同的字段上都建有索引, Coherence能取回多个结果接,包括"所有的鞋","所有的红鞋","所有的女鞋","所有的26码鞋"(每个对应不同的字段索引). 这里重要的一点是Coherence只要查询中每个字段都有索引,就不必自己检查每个对象. 在Coherence索引上的对象集的实现都是哈希集(使用对象的主键来引用对象).为了选出两个哈希集的交集,Coherence必须轮询其中一个结合然后和另外一个结合做比较.如果一个集合很小,则查询会非常快. 但如果两个结果都有上千条纪录则会花很多的时间.

这个方法也有局限性. 在上述的例子中,所有4个集合产生的索引会很多,所以求交集的操作会很费时间. 有时不用索引反而会提高查询性能(例如女鞋的结果集很大时). 查询条件(Coherence中叫做filter)的顺序也很重要,因为Coherence不会做全局的查询优化. 不过这个方法一般会比数据库的多条件查询要好, 但这个查询例子还不是特别适合内存数据网格.

Lucence的位图索引

Lucene是个java实现的全文文本搜索引擎. 惊喜的是全文本搜索和多条件查询十分类似. Lucene可以直接处理我们的查询. 

Lucene使用压缩的位图来储存倒排索引(即不是BTress也不是哈希表).压缩位图有两个重要的特性: 1,更小的空间2,可以不解压缩做binary operations(例如求交集). 类似Coherence, Lucene可以使用所有的四个索引来做查询.但是不像Coherence,使用了压缩位图的Lucene可以很快的处理Coherence提到的四个集合的交集操作.即使每个集合都上千条纪录也是小菜一碟.

使用压缩位图让Lucene是处理多条件查询的强力工具,在实践中Lucene能够比数据库或是Coherence处理此类型查询要快上个数量级.

但是使用位图也有代价. 实践中压缩位图的更新需要重写整个集合. 这意味着基于位图索引的更新操作代价是极高的. Lucene正在花大力气改进这个根本性的局限点.(例如索引分段和logarithmic merging under hood), 但是Lucenne的索引更新代价通常还是要比数据库和Coherence要高.

最佳组合:

如果你正在使用Coherence并且羡慕Lucene的搜索能力,你可以尝试grid4search项目.其容许使用Lucene替换Coherence内置索引.



原文出处:http://blog.griddynamics.com/2011/04/indexes-rdbms-vs-coherence-vs-lucene.html


推荐阅读
  • 本文介绍了数据库的存储结构及其重要性,强调了关系数据库范例中将逻辑存储与物理存储分开的必要性。通过逻辑结构和物理结构的分离,可以实现对物理存储的重新组织和数据库的迁移,而应用程序不会察觉到任何更改。文章还展示了Oracle数据库的逻辑结构和物理结构,并介绍了表空间的概念和作用。 ... [详细]
  • 本文介绍了如何使用php限制数据库插入的条数并显示每次插入数据库之间的数据数目,以及避免重复提交的方法。同时还介绍了如何限制某一个数据库用户的并发连接数,以及设置数据库的连接数和连接超时时间的方法。最后提供了一些关于浏览器在线用户数和数据库连接数量比例的参考值。 ... [详细]
  • 如何自行分析定位SAP BSP错误
    The“BSPtag”Imentionedintheblogtitlemeansforexamplethetagchtmlb:configCelleratorbelowwhichi ... [详细]
  • 本文是一位90后程序员分享的职业发展经验,从年薪3w到30w的薪资增长过程。文章回顾了自己的青春时光,包括与朋友一起玩DOTA的回忆,并附上了一段纪念DOTA青春的视频链接。作者还提到了一些与程序员相关的名词和团队,如Pis、蛛丝马迹、B神、LGD、EHOME等。通过分享自己的经验,作者希望能够给其他程序员提供一些职业发展的思路和启示。 ... [详细]
  • CSS3选择器的使用方法详解,提高Web开发效率和精准度
    本文详细介绍了CSS3新增的选择器方法,包括属性选择器的使用。通过CSS3选择器,可以提高Web开发的效率和精准度,使得查找元素更加方便和快捷。同时,本文还对属性选择器的各种用法进行了详细解释,并给出了相应的代码示例。通过学习本文,读者可以更好地掌握CSS3选择器的使用方法,提升自己的Web开发能力。 ... [详细]
  • Oracle Database 10g许可授予信息及高级功能详解
    本文介绍了Oracle Database 10g许可授予信息及其中的高级功能,包括数据库优化数据包、SQL访问指导、SQL优化指导、SQL优化集和重组对象。同时提供了详细说明,指导用户在Oracle Database 10g中如何使用这些功能。 ... [详细]
  • 本文讨论了如何优化解决hdu 1003 java题目的动态规划方法,通过分析加法规则和最大和的性质,提出了一种优化的思路。具体方法是,当从1加到n为负时,即sum(1,n)sum(n,s),可以继续加法计算。同时,还考虑了两种特殊情况:都是负数的情况和有0的情况。最后,通过使用Scanner类来获取输入数据。 ... [详细]
  • 本文介绍了九度OnlineJudge中的1002题目“Grading”的解决方法。该题目要求设计一个公平的评分过程,将每个考题分配给3个独立的专家,如果他们的评分不一致,则需要请一位裁判做出最终决定。文章详细描述了评分规则,并给出了解决该问题的程序。 ... [详细]
  • 知识图谱——机器大脑中的知识库
    本文介绍了知识图谱在机器大脑中的应用,以及搜索引擎在知识图谱方面的发展。以谷歌知识图谱为例,说明了知识图谱的智能化特点。通过搜索引擎用户可以获取更加智能化的答案,如搜索关键词"Marie Curie",会得到居里夫人的详细信息以及与之相关的历史人物。知识图谱的出现引起了搜索引擎行业的变革,不仅美国的微软必应,中国的百度、搜狗等搜索引擎公司也纷纷推出了自己的知识图谱。 ... [详细]
  • 本文详细介绍了Linux中进程控制块PCBtask_struct结构体的结构和作用,包括进程状态、进程号、待处理信号、进程地址空间、调度标志、锁深度、基本时间片、调度策略以及内存管理信息等方面的内容。阅读本文可以更加深入地了解Linux进程管理的原理和机制。 ... [详细]
  • 关于我们EMQ是一家全球领先的开源物联网基础设施软件供应商,服务新产业周期的IoT&5G、边缘计算与云计算市场,交付全球领先的开源物联网消息服务器和流处理数据 ... [详细]
  • 本文介绍了一个在线急等问题解决方法,即如何统计数据库中某个字段下的所有数据,并将结果显示在文本框里。作者提到了自己是一个菜鸟,希望能够得到帮助。作者使用的是ACCESS数据库,并且给出了一个例子,希望得到的结果是560。作者还提到自己已经尝试了使用"select sum(字段2) from 表名"的语句,得到的结果是650,但不知道如何得到560。希望能够得到解决方案。 ... [详细]
  • 本文讨论了在数据库打开和关闭状态下,重新命名或移动数据文件和日志文件的情况。针对性能和维护原因,需要将数据库文件移动到不同的磁盘上或重新分配到新的磁盘上的情况,以及在操作系统级别移动或重命名数据文件但未在数据库层进行重命名导致报错的情况。通过三个方面进行讨论。 ... [详细]
  • ALTERTABLE通过更改、添加、除去列和约束,或者通过启用或禁用约束和触发器来更改表的定义。语法ALTERTABLEtable{[ALTERCOLUMNcolu ... [详细]
  • 深入理解CSS中的margin属性及其应用场景
    本文主要介绍了CSS中的margin属性及其应用场景,包括垂直外边距合并、padding的使用时机、行内替换元素与费替换元素的区别、margin的基线、盒子的物理大小、显示大小、逻辑大小等知识点。通过深入理解这些概念,读者可以更好地掌握margin的用法和原理。同时,文中提供了一些相关的文档和规范供读者参考。 ... [详细]
author-avatar
书友53034809
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有