Hadoop平台常用的SQl优化方法!

要正确的优化SQL,必须能快速定位性能瓶颈点,或者说快速找到SQL主要的开销所在。最慢的设备通常是瓶颈点所在,如文件下载时的瓶颈点可能是网络速度,本地文件复制时的瓶颈点可能在于硬盘性能。

为了快速找到SQL的性能瓶颈点,首先需要读者对各种设备的性能数据有一些基本的认识,如千兆网络带宽是1000Mbps,硬盘转速为每分钟7200/10000转等。

下图数据给出了一些当前主流的计算机性能指标。

图1 I/O各层次硬件性能汇总

如上图所示,每种设备基本上都有两个重要指标:

延时(响应时间):反映硬件的突发处理能力。

带宽(吞吐量):反映硬件持续处理能力。

通过比较这两种指标,可以发现计算机各系统硬件性能从高到低依次为:CPU→Cache(L1-L2-L3)→内存→SSD硬盘→网络→硬盘。

比较性能之后,我们再看一下每种硬件在Hadoop系统进行SQL运算时负责的主要工作:

CPU及内存:缓存数据访问、比较、排序、事务检测、SQL解析、函数或逻辑运算、JOIN、数据加解密、加解压等;

网络:结果或者Shuffle数据的传输、SQL请求、远程数据访问等;

硬盘:数据访问、数据写入、日志记录、外排序、Shuffle等。

将以上陈列的各硬件性能指标及其工作内容结合考虑,在Hadoop集群中提升SQL的执行性能就是要尽量做到以下四点:

减少数据访问(减少磁盘访问)

减少中间结果量(减少网络传输或磁盘访问)

减少交互次数(减少网络传输、减少调度开销)

改进算法,减少服务器CPU开销(减少CPU及内存开销)

注:实际优化时,除了以上四点还应注意任务分配要均匀且大小适中。

总而言之,优化的基本思想就是反复迭代,合理利用资源,综合平衡各种开销,以求达到最优效果。下面将简单介绍这四种优化思路,以及分别可采用的方法。

1. 减少数据访问

传统关系型数据库例如MySQL、Oracle等,通常通过提供索引来实现减少数据访问、提升访问速度,但是由于Hadoop不维护键(Key)的特性,因而SQL on Hadoop引擎一般不提供对传统索引的支持,或者功能不像传统索引一样完备。

为了达到和索引相似的优化目的,即加快过滤扫描,SQL on Hadoop产品通常提供其他功能用以弥补。以星环科技的Inceptor为例,其本身并没有可用于控制的传统意义上的索引,但是提供了分区、分桶,以及MinMaxFilter、BloomFilter以及RowFilter等用于批量过滤数据的过滤器。这些功能的原理通常是通过把相似、相关或者相等的数据进行归类以减少查询搜索的范围,或者建立基于列式存储的扫描方式尽可能的减少无关数据的读取。使用者需要结合实际语句,把这些功能进行高效组合,合理运用在刀刃上。

2. 返回更少的数据

返回更少的数据就是要求在构造SQL语句时,只SELECT需要的列。因为每个字段的提取都是一个复杂的解析过程,且占用内存,所以为了减少不必要的查询时间,请读者最好仅返回需要的字段。比如减少“SELECT *”的使用,因为大多数情况是不需要所有字段的数据的。

【例1】如果某用户提交了这样的语句,但是实际需要的只有id、name两个字段:

SELECT * FROM product WHERE company_id = 456723

LIMIT 100;

为了加快执行速度,建议将语句写为:

SELECT id, name FROM product

WHERE company_id = 456723

LIMIT 10;

另外若SELECT的结果是用于判断某些条件是否成立,例如EXISTS操作,就更加没必要返回所有数据:

【例2】某个包含关联的语句,在优化调整前,EXISTS内部返回了满足条件的所有字段值:

SELECT … FROM table_name_2 WHERE

… EXISTS (

SELECT * FROM table_name_1

WHERE table_name_1.col1 = table_name_2.col1

);

但是EXISTS的返回仅用于判断满足条件的记录存在与否,所以EXISTS内部无需返回所有字段。因此可以将EXISTS子句中的“SELECT *”优化为“SELECT 1”:

SELECT … FROM table_name_2 WHERE

… EXISTS (

SELECT 1 FROM table_name_1

WHERE table_name_1.col1 = table_name_2.col1

);

3. 减少交互次数

减少交互次数就是减少网络通信的交互次数。这里分享与此相关的三种优化情况。

Batch DML

批量方式处理DML可以大幅度减少和服务器的交互次数。Inceptor数据库访问框架提供了批量提交的接口以服务于大量插入数据。当用户一次性往一个表中插入1000万条数据时,试想如果采用普通的Insert,将和服务器发生1000万次交互,按每秒钟向数据库服务器提交10000次估算,完成所有工作需要消耗1000秒。但是如果采用批量提交模式,每1000条提交一次,和服务器的交互次数就减少至1万次,交互次数大大减少,耗时缩短为原来的千分之一。

采用Batch操作虽然不会大量减少数据库服务器的物理I/O,但是会大幅减少客户端与服务端的交互次数,从而降低多次发起的网络延时开销,以及数据库的CPU开销。

In List

进行数据扫描时,有时会遇到这样的情况:到手多个ID,需要查询与这些ID相关的记录。有两种方式实现:单条提交或者批量提交。

单条处理就是采用一个ID发一个请求的方式传送给数据库:

for: var in ids[] do begin

SELECT * FROM table_name WHERE id=:var;

end;

这种方法会增加与服务器的交互次数,显然和减少交互次数的思想背道而驰,固然是不推荐的。建议用ID InList的方式批量提交,可以把多次交互压缩在一次访问中完成,加速查询:

SELECT * FROM table_name

WHERE id IN ids[];

使用存储过程

Inceptor支持存储过程,合理的利用存储过程有助于提高系统性能。存储过程是由SQL语句组成的完成特定功能的代码块。每个代码块在创建时都需要命名,用户通过访问对应名称调用它们。存储过程中的代码都是已经编译过的,所以调用的时候可以跳过编译阶段直接执行,而且由于其直接存储在数据库中,可以避免SQL语句的重复传输。

总体而言使用存储过程有以下两方面的好处:

减少编译次数提高了执行效率。

在网络交互中代替了大量的SQL语句,使用者只需传递一些必要参数,帮助减少网络通信量,提升通信效率。

4. 减少数据库服务器

CPU运算SQL中会包含各种各样的操作和计算要求CPU参与运算,其中有一些计算并非必须,可以人为避免。例如,进行对比运算时,对于不匹配的类型,系统要对操作数进行类型转换,导致加重CPU负担。所以,对于数字和日期类型,建议用户在执行计算前先进行类型转换,使各操作数的类型匹配,或者建表时尽可能的把字段规划成相同的数据类型。

另外,对于SQL中的逻辑运算符,Inceptor通常对普通比较运算符(如等于、不等)有较好的表现,但是对于服务器CPU需求量很高的操作,需要用户保持警惕。如LIKE操作,该模糊查询对CPU的要求一般较高,特别是检查的记录有上万条及以上时,系统表现比较糟糕。建议用户根据业务语义尽量用In-List实现LIKE,在In-List中包含LIKE所有可能的匹配选项。

【例3】如下所示模糊查询语句:

SELECT * FROM table_name

WHERE column_name LIKE ‘%abc%’;

若已知该列字段值仅有三种取值‘cabc’、‘abce’、‘cabe’,上面的语句可以等价为这样的表达方式:

SELECT * FROM table_name

WHERE column_name IN (‘cabc’, ‘abce’, ‘cabe’);

【例4】如果In-List数据可用一条SELECT语句查询得到,最好让一张中间小表作为In列表内部数据,然后采用内外查询关联的方式进行检索:

SELECT * FROM table_name

WHERE column_name IN (

SELECT col_name FROM tbl WHERE gender = ‘f’

);

总结本文分享了四种在Hadoop平台中常用的SQL优化思路,实际上每种思路在具体应用时都可以引申出很多不同的方法,介绍这些思路的目的在于为用户在选择SQL优化手段时提供一些明确方向。

最后大致总结一下这些优化思路的适用场合:

在过滤扫描阶段考虑如何减少数据访问;

构造SELECT子句时应思考应该如何减少返回数据;

当执行涉及向服务器发起交互请求的操作时,应当选择减少交互次数的合适方法;

必要时进行人工处理以减少不必要的CPU计算。

如果用户能够考虑并兼顾这四个方面,相信由此构造的SQL语句会在Hadoop平台中有更好的执行性能。

原文地址:http://www.dashengzb.cn/articles/a-336.html

(更多大数据与商业智能领域干货、或电子书,可添加个人微信号(dashenghuaer))

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 212,884评论 6 492
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,755评论 3 385
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 158,369评论 0 348
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,799评论 1 285
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,910评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,096评论 1 291
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,159评论 3 411
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,917评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,360评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,673评论 2 327
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,814评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,509评论 4 334
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,156评论 3 317
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,882评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,123评论 1 267
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,641评论 2 362
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,728评论 2 351

推荐阅读更多精彩内容