|
计算机存储的容量限制仍然日益成为IT系统的瓶颈。其主要原因有两个:第一,信息革命导致人们产生了比过去多得多的数据。巨大的数据库系统每时每刻都在产生海量的新数据。第二,随着计算机存储能力的增长,人们倾向于永久性保存所有的数据。例如,在信息革命早期,证券交易系统往往只保存近一段时间的交易细节数据。如今,人们倾向于保存所有能够被保存的数据:每一次交易,每一通电话,网站的每一次点击,交换机中的每一回通信等。
在这种趋势下,计算机存储承担着越来越沉重的压力。尤其是在企业级应用中,为了保存海量数据而在存储上投入的成本,往往已经到了令人吃惊的地步。
在数据库中使用压缩技术,是为了解决(或者至少缓解)这种压力所做出的努力之一。这种技术的定义十分简单:对存储在数据库中的数据进行压缩,从而减少占用的磁盘空间,同时又尽量不影响数据库的其他操作。
很容易想象这一技术产生的后果。被压缩后的数据能够显著地减少占用的磁盘空间,从而降低整个系统的存储成本。然而对数据进行压缩和解压缩,需要更多的CPU时间。在对速度要求十分苛刻的数据库系统中,这种CPU时间的额外支出,是否会导致效率的严重降低呢?
让我们全面地审视压缩技术引起的得失。在CPU时间上,会有额外的支出。但是,由于压缩后的数据占用的磁盘空间减少了,这意味着系统用于I/O的时间也会相应的减少。众所周知,数据库系统最大的瓶颈在于I/O:I/O速度的增长却远远跟不上CPU按照摩尔定律的增长。因此,从CPU时间上支出的成本,可以在I/O速度的提高上补偿回来,而且还可能有盈余。压缩后的数据库,不但会占用更少的磁盘空间,甚至还可能有更快的速度。
然而在实际项目中,还要考虑到多种因素的权衡,情况可能会非常复杂。幸运的是,主流的几种关系数据库在实践中都已经正式支持压缩技术。目前,数据库压缩技术主要仍然被应用于数据密集型的OLAP,而不是运算密集型的OLTP,但这并不意味着它不能被应用于OLTP。
压缩方式
目前,几乎所有的关系型数据库中应用的压缩方式,都是基于字典的压缩方式。基本原理是,将数据中重复出现的信息抽取出来,并用比较简短的符号予以代替,从而达到压缩的效果。举例来说,如果数据中重复出现了“PersonalComputer”这个字符串,那么它就会被识别为一个模式(Pattern),然后所有这个字符串出现的地方都会被一个对应的符号(Symbol)代替,比如数字1。所有的模式和对应的符号都会被存储在字典里面(Dictionary),字典被用于压缩和解压缩(也就是对Pattern和Symbol进行相互替换)。当然,真实的应用比这要复杂得多。但是,理解了字典压缩的原理以后,我们已经可以从不同的角度对不同的压缩技术进行区分。
按建立字典的方式区分:手工建立字典和自动建立字典。手工建立字典,意味着数据库不能自动搜索数据中的重复数据,必须人工输入所有的模式才能建立字典。这种方式出现在数据库压缩技术的早期,目前已经基本被淘汰。自动建立字典则意味着数据库会自动搜索模式而无需人工干预。
按字典应用的范围区分:表级别的字典和块级别的字典。表级别的字典意味着在整个表的范围内搜索模式并建立一个唯一的字典,而块级别的字典则在每一个块上建立单独的字典。其中,块是关系型数据库中的一个术语,是存储的最小单位。
按存储的方式区分:列压缩和行压缩。这涉及列存储和行存储的概念。行存储表示数据库中包含不同字段的同一行被连续存放。列存储则表示包含不同行的同一字段数据被连续存放。同一字段的数据出现重复的可能性较大,这意味着基于列的压缩可能有更高的效率,但这和传统关系型数据库的存储方式相悖。由于二者互有利弊,数据库厂商往往通过一些技巧来避免其缺陷,使之适应实际使用,甚至混合使用这两种压缩方式。
压缩相关的操作
虽然关系型数据库使用的压缩算法本身不太复杂,但是由于压缩技术改变了数据存储的底层结构,因此涉及数据库操作的方方面面。下面是一些主要的相关操作:
数据查询。当接收到查询请求时,数据库系统从磁盘中读取已被压缩的数据,必须先经过一个解压的过程,将数据还原为未压缩的形式,再返回给查询请求。
数据更新。当进行Insert和Update操作时,数据需要经过压缩之后才被存储。理论上来说,Delete操作只需要简单地删除数据,而无需进行压缩或解压缩。但是事实上,在某些自适应的压缩技术中,对已有数据的更新到达某一阈值时,会导致字典的自动更新(因为字典已经不能再适应当前的数据)。这意味着,IUD操作都有可能导致字典的重新创建(或删除)。
数据装载。这和插入数据的过程类似,数据将会先被压缩然后被存储。在某些情况下(例如,当DB2的AutomaticDictionaryCreation技术被启用时),装载数据时还可能同时创建字典。
表整理。在整理表时,根据当前表被标识为压缩或未压缩,将会对数据进行相应的压缩或者解压缩处理。表整理是对整个表进行充分压缩的有效手段。
压缩率评估。数据库一般会提供一个操作,在未被压缩(或未被完全压缩)的数据表上进行评估,预测能达到多高的压缩率。
索引(Index)压缩。索引压缩的算法与关系型数据压缩不太一样,本文不进行深入讨论。
大对象(LOB)压缩。大对象不使用关系型数据的行存储或列存储方式,因此也不适用上述的算法。
日志(Log)。日志中需要保存和压缩操作相关的信息,以保证数据的一致性。
备份与恢复。在备份与恢复操作时,需要进行相应的数据压缩和解压缩处理。
压缩相关的命令
虽然压缩涉及非常复杂的数据库内部机制,但理论上来说,压缩后的数据库对于使用者是透明的,所有的压缩和解压缩过程都隐藏在数据库内部。因此,在绝大部分情况下,使用者不需要进行额外的操作,甚至不需要知道数据库是否已经被压缩过。
当然,仍然有一些与特定的压缩相关的数据库命令。下面以DB2V9.7为例,作一简单讨论。
当创建一个表的时候,可指定该表使用压缩。语法如下:
view sourceprint?1 CREATETABLECUSTOMER( … )COMPRESSYES;
it知识库:关系型数据库中的压缩技术,转载需保留来源!
郑重声明:本文版权归原作者所有,转载文章仅为传播更多信息之目的,如作者信息标记有误,请第一时间联系我们修改或删除,多谢。