我有一个查询使用很多容器和很多内存。 (使用的内存的97%)。 有没有一种方法可以设置查询中使用的容器数并限制最大内存? 该查询正在Tez上运行。
预先感谢
答案 0 :(得分:2)
控制映射器的数量:
映射器的数量取决于各种因素,例如数据如何在节点之间分布,输入格式,执行引擎和配置参数。另请参见How initial task parallelism works
MR使用CombineInputFormat,而Tez使用分组拆分。
Tez:
set tez.grouping.min-size=16777216; -- 16 MB min split
set tez.grouping.max-size=1073741824; -- 1 GB max split
增加这些数字以减少正在运行的映射器的数量。
映射器也在数据所在的数据节点上运行,这就是为什么手动控制映射器的数量不是一件容易的事,并非总能合并输入的原因。
控制减速器的数量:
根据确定的减速器数量
mapreduce.job.reduces
mapred.job.tracker
为“本地”时被忽略。 Hadoop默认将此值设置为1,而Hive使用-1作为默认值。通过将此属性设置为-1,Hive将自动计算出减速器的数量。 hive.exec.reducers.bytes.per.reducer
-Hive 0.14.0及更低版本中的默认值为1 GB。
也hive.exec.reducers.max
-将使用的最大减速器数量。如果mapreduce.job.reduces
为负数,Hive在自动确定减速器数量时将以此为最大减速器数量。
只需设置hive.exec.reducers.max=<number>
即可限制运行的减速器数量。
如果要增加reducer的并行度,请增加hive.exec.reducers.max并减少hive.exec.reducers.bytes.per.reducer。
内存设置:
set tez.am.resource.memory.mb=8192;
set tez.am.java.opts=-Xmx6144m;
set tez.reduce.memory.mb=6144;
set hive.tez.container.size=9216;
set hive.tez.java.opts=-Xmx6144m;
默认设置意味着实际的Tez
任务将使用映射器的内存设置:
hive.tez.container.size = mapreduce.map.memory.mb
hive.tez.java.opts = mapreduce.map.java.opts
详细阅读:Demystify Apache Tez Memory Tuning - Step by Step
我建议先优化查询。如果可能,请使用map-joins,使用矢量化执行,如果要编写分区表,请添加distribute by partitin key
,以减少reducer上的内存消耗,当然还要编写好的sql。