Spark执行器OOM问题

时间:2019-01-25 07:23:28

标签: apache-spark

我有一个典型的批处理作业,它从云存储中读取CSV,然后进行一堆连接和聚合,整个文件不超过3G。但是在将结果写回到存储时,我总是收到OOM异常,我有两个执行器,每个执行器都有80G的RAM,这没有任何意义,这是我的Spark UI和异常的屏幕截图。并且建议,如果我的代码在内存方面是超级次优的,为什么它不显示在spark UI上? enter image description here

enter image description here

更新:源代码太复杂了,无法在此处显示,但是我发现根本原因是多重连接。

Dataset<Row> ret = something dataframe
for (String cmd : cmds) {
   ret = ret.join(processDataset(ret, cmd), "primary_key")
}

因此,每个processDataset(ret,cmd),如果自己运行,速度都非常快,但是如果您多次进行这种for循环联接,例如10或20次,它将得到很多慢得多,并出现OOM问题。

1 个答案:

答案 0 :(得分:1)

当我的内存有问题时,请检查以下内容:

  • 具有更多的执行程序(超过2个,由spark-submit中的total-executor-cores和SparkSession中的spark.executor.core定义)
  • 每个执行器的内核数较少(3-5)。您有14个比建议的数量(spark.executor.core)多得多
  • 为执行者(spark.executor.memory)添加记忆力
  • 向驱动程序添加内存(火花提交脚本中的driver-memory
  • 制作更多分区(使分区更小)(在SparkSession中为.config("spark.sql.shuffle.partitions", numPartitionsShuffle)
  • 查看“分阶段任务”的PeakExecutionMemory(要打开的其他指标之一)选项卡,看它是否不大
  • 如果在“代理”选项卡中使用Mesos,则可以看到每个驱动程序和执行程序的实际内存使用情况(请参阅此答案How to get Mesos Agents Framework Executor Memory
  • 查看代码中的explain来分析执行计划
  • 查看您的联接之一是否不会通过重复复制多行来消耗您的记忆力