sql优化
https://www.cnblogs.com/joechinochl/articles/6009143.html
用IN来替换OR
避免函数
不使用子查询
少用like
用limit
分组禁止排序GROUP BY goods_id ORDER BY NULL;
hive的查询注意事项以及优化总结 :
优化暂时用
1.count distinct的操作,先转成group,再count
按照分区查询获取需要的字段
2减少每个阶段的数据量,尽量用上分区字段,同时只选择后面需要使用到的列,最大限度的减少参与 join 的数据量。
小表 join 大表
on 条件使用相同字段,那么它们会合并为一个 MapReduce Job节省时间
3优化sql,将where条件放到子查询中,查询效率将会提高很多。
4先聚集,然后联合数据表https://segmentfault.com/a/1190000000412056
1:尽量尽早地过滤数据,减少每个阶段的数据量,对于分区表要加分区,同时只选择需要使用到的字段
2、对历史库的计算经验 (这项是说根据不同的使用目的优化使用方法)
历史库计算和使用,分区
3:尽量原子化操作,尽量避免一个SQL包含复杂逻辑
可以使用中间表来完成复杂的逻辑
4 join操作 小表要注意放在join的左边(有的公司很多都小表放在join的右边)否则会引起磁盘和内存的大量消耗
5:如果union all的部分个数大于2,或者每个union部分数据量大,应该拆成多个insert into 语句,实际测试过程中,执行时间能提升50%
在使用with as提取公共条件时,只查询需要使用到的字段即可。如果原始表中的字段较多,提取无用字段会增加Hive的工作量(尤其是多表join时)。另外,order by对资源的占用也比较多,Hive会对全表进行扫描再进行排序。如果没有排序筛选的需求(如limit),可以先不用order by查询出结果,然后利用其它工具对查询结果进行排序。
优化2
当一个 Hive 表的查询大多数情况下,会根据某一个字段进行筛选时,那么非常适合创建为分区表。
--分桶
CREATE TABLE bucketed_user (id INT) name STRING)
CLUSTERED BY (id) INTO 4 BUCKETS;
语法和参数层面优化
https://juejin.im/post/5d27f45851882569755f4c7b
1可以只读取查询中所需要用到的列,而忽略其他的列。这样做可以节省读取开销,中间表存储开销和数据整合开销
2在查询的过程中只选择需要的分区,可以减少读入的分区数目,减少读入的数据量。
合并小文件
Map 输入合并
复制代码Map/Reduce输出合并
合理控制 map/reduce 任务数量
默认的 mapper 个数计算方式
输入文件总大小:total_size; hdfs 设置的数据块大小: dfs_block_size default_mapper_num = total_size/dfs_block_size
自己控制:set mapred.map.tasks=10; 参数设置只有在大于默认生效
合理控制reducer数量
数量过多,一个 reducer 会产生一个结数量果文件,很多小文件合并问题
reducer 数量过少,这样一个 reducer 就需要处理大量的数据,并且还有可能会出现数据倾斜的问题,使得整个查询耗时长
orderby优化
不要在中间的大数据集上进行排序。如果最终结果较少,可以在一个reduce上进行排序时,那么就在最后的结果集上进行order by
取排序后的前N条数据,可以使用distribute by和sort by在各个reduce上进行排序后前N条
## COUNT DISTINCT优化
-- 优化前(只有一个reduce,先去重再count负担比较大):
select count(distinct id) from table1;
-- 优化后(启动两个job,一个job负责子查询(可以有多个reduce),另一个job负责count(1)): 不同记录少的时候优化明显1/1000,多的时候不好3/10
select count(1) from (select distinct id from table1) tmp;
select count(1) from (select id from table1 group by id) tmp;
--一次读取多次插入
from sale_detail
insert overwrite table sale_detail_multi partition (sale_date='2010', region='china' )
select shop_name, customer_id, total_price where .....
insert overwrite table sale_detail_multi partition (sale_date='2011', region='china' )
select shop_name, customer_id, total_price where .....;
load data导入数据比insert into快多了;
1少用函数
2、count(distinct ),在数据量大的情况下,效率较低,如果是多count(distinct )效率更低,因为count(distinct)是按group by 字段分组,按distinct字段排序,一般这种分布方式是很倾斜的。举个例子:比如男uv,女uv,像淘宝一天30亿的pv,如果按性别分组,分配2个reduce,每个reduce处理15亿数据。
3、group by, order by 后面跟数字,指的是 select 后面选择的列(属性),1 代表第一个列(属性),依次类推