我的脚本由于处理太多分区的堆空间问题而失败。为了避免这个问题,我试图将所有分区插入到单个分区中,但我面临以下错误
FAILED: SemanticException [Error 10044]: Line 1:23无法插入到目标表中,因为列数/类型不同" 20121-01-16 ":表insclause-0有78列,但查询有79列
set hive.exec.dynamic.partition=true;
set mapreduce.reduce.memory.mb=6144;
set mapreduce.reduce.java.opts=-Xmx5g;
set hive.exec.dynamic.partition=true;
insert overwrite table db_temp.travel_history_denorm partition (start_date='2021-01-16')
select * from db_temp.travel_history_denorm_temp_bq
distribute by start_date;```
Can someone please suggest what is the issue, I checked the schema for the tables it is the same. ?
您正在插入到静态分区(在目标表分区子句中指定的分区值),在这种情况下,您不应该在选择分区列。select *返回分区列(最后一个),这就是为什么查询失败,它应该是没有分区列:
静态分区插入:
insert overwrite table db_temp.travel_history_denorm partition (start_date='2021-01-16')
select col1, col2, col3 ... --All columns except start_date partition column
from ...
动态分区:
insert overwrite table db_temp.travel_history_denorm partition (start_date)
select * --All columns in the same order, including partition
from ...
添加distribute by
触发额外的reduce步骤,所有记录根据distribute by
分组,每个reducer接收单个分区。当您在每个reducer中加载许多动态分区时,这有助于解决OOM问题。如果没有分布,每个reducer将在每个分区中创建文件,同时保持太多的缓冲区。
除了distribute by
,您还可以设置每个reducer的最大字节数。此设置将限制单个reducer处理的数据量,也可能有助于OOM:
set hive.exec.reducers.bytes.per.reducer=16777216; --adjust for optimal performance
如果这个数字太小,它将触发太多的减速机,如果太大-则每个减速机将处理太多的数据。相应调整。
也可以尝试动态分区加载的设置:
set hive.optimize.sort.dynamic.partition=true;
启用后,动态分区列将全局排序。这样,我们可以为每个分区只保留一个打开的记录写入器值,从而降低reducer的内存压力。
你可以组合所有这些方法:按分区键分发,bytes.per.reducer和sort.dynamic.partition用于动态分区加载。
异常消息也可以帮助理解OOM发生的确切位置并相应地修复。