Hadoop MapReduce小文件内存不足

时间:2015-11-20 19:26:09

标签: java hadoop amazon-web-services mapreduce elastic-map-reduce

我在Hadoop上针对大约300万个小文件运行MapReduce作业(我知道,但是我知道,但我们无能为力 - 它是我们源代码的本质系统)。

我们的代码并不特别 - 它使用CombineFileInputFormat将一堆这些文件包装在一起,然后解析文件名以将其添加到文件的内容中,并吐出一些结果。容易腻。

因此,我们在HDFS中有大约300万~7kb的文件。如果我们针对这些文件的一小部分(一个文件夹,可能是10,000个文件)运行我们的任务,我们就不会遇到麻烦。如果我们针对完整的文件列表运行它,则会出现内存不足错误。

错误出现在STDOUT

#
# java.lang.OutOfMemoryError: GC overhead limit exceeded
# -XX:OnOutOfMemoryError="kill -9 %p"
#   Executing /bin/sh -c "kill -9 15690"...

我假设发生的事情就是这样 - 无论JVM正在运行什么,定义输入拆分的过程都会变得不堪重负,试图处理300万个文件,它使用了太多的内存,并且YARN正在杀死它。我愿意在这个理论上得到纠正。

所以,我需要知道的是为容器增加YARN的内存限制,该容器计算输入分割,而不是为映射器或缩减器。然后,我需要知道如何使这个生效。 (我已经在Google上广泛搜索过,但是多年来Hadoop的所有迭代都很难找到适用于最新版本的解决方案......)

这是Hadoop 2.6.0,在AWS Elastic MapReduce 4.2.0上使用MapReduce API,YARN框架。

2 个答案:

答案 0 :(得分:1)

我会启动一个新的EMR集群并在其上抛出一个更大的主实例来查看是否存在问题。

--instance-groups InstanceGroupType=MASTER,InstanceCount=1,InstanceType=m3.4xlarge InstanceGroupType=CORE,InstanceCount=1,InstanceType=m3.xlarge

如果在配置输入拆分时主站的内存不足,您可以修改配置 EMR Configuration

答案 1 :(得分:0)

您可以使用以下任何方法将它们合并到可管理的更大文件中,而不是在300万个单独文件上运行MapReduce。 1.从小文件创建Hadoop存档(HAR)文件。 2.使用MapReduce程序为每个10K-20K文件创建序列文件。 3.使用forqlift工具从单个小文件创建序列文件。 4.使用Hadoop-Crush将小文件合并为更大的文件。

准备好较大的文件后,可以在整个数据集上运行MapReduce。