Spark:广播对象时内存不足

Posted

技术标签:

【中文标题】Spark:广播对象时内存不足【英文标题】:Spark: out of memory when broadcasting objects 【发布时间】:2016-07-27 21:58:05 【问题描述】:

我尝试广播一个不太大的地图(以文本文件形式保存到 HDFS 时约为 70 MB),但出现内存不足错误。我尝试将驱动程序内存增加到 11G,将执行程序内存增加到 11G,但仍然出现相同的错误。 memory.fraction 设置为 0.3,缓存的数据也不多(小于 1G)。

当地图只有 2 MB 左右时,没有问题。我想知道广播对象时是否有大小限制。如何使用更大的地图解决这个问题?谢谢!

Exception in thread "main" java.lang.OutOfMemoryError: Java heap space
    at java.util.IdentityHashMap.resize(IdentityHashMap.java:469)
    at java.util.IdentityHashMap.put(IdentityHashMap.java:445)
    at org.apache.spark.util.SizeEstimator$SearchState.enqueue(SizeEstimator.scala:159)
    at org.apache.spark.util.SizeEstimator$.visitArray(SizeEstimator.scala:229)
    at org.apache.spark.util.SizeEstimator$.visitSingleObject(SizeEstimator.scala:194)
    at org.apache.spark.util.SizeEstimator$.org$apache$spark$util$SizeEstimator$$estimate(SizeEstimator.scala:186)
    at org.apache.spark.util.SizeEstimator$.estimate(SizeEstimator.scala:54)
    at org.apache.spark.util.collection.SizeTracker$class.takeSample(SizeTracker.scala:78)
    at org.apache.spark.util.collection.SizeTracker$class.afterUpdate(SizeTracker.scala:70)
    at org.apache.spark.util.collection.SizeTrackingVector.$plus$eq(SizeTrackingVector.scala:31)
    at org.apache.spark.storage.MemoryStore.unrollSafely(MemoryStore.scala:278)
    at org.apache.spark.storage.MemoryStore.putIterator(MemoryStore.scala:165)
    at org.apache.spark.storage.MemoryStore.putIterator(MemoryStore.scala:143)
    at org.apache.spark.storage.BlockManager.doPut(BlockManager.scala:801)
    at org.apache.spark.storage.BlockManager.putIterator(BlockManager.scala:648)
    at org.apache.spark.storage.BlockManager.putSingle(BlockManager.scala:1006)
    at org.apache.spark.broadcast.TorrentBroadcast.writeBlocks(TorrentBroadcast.scala:99)
    at org.apache.spark.broadcast.TorrentBroadcast.<init>(TorrentBroadcast.scala:85)
    at org.apache.spark.broadcast.TorrentBroadcastFactory.newBroadcast(TorrentBroadcastFactory.scala:34)
    at org.apache.spark.broadcast.BroadcastManager.newBroadcast(BroadcastManager.scala:63)
    at org.apache.spark.SparkContext.broadcast(SparkContext.scala:1327)

编辑: 根据 cmets 添加更多信息:

我使用spark-submit在客户端模式下提交编译好的jar文件。 Spark 1.5.0 spark.yarn.executor.memoryOverhead 600 set("spark.kryoserializer.buffer.max", "256m") set("spark.speculation", "true") set("spark.storage.memoryFraction", "0.3") set("spark.driver.memory", "15G") set("spark.executor.memory", "11G") 我试过 set("spar.sql.tungsten.enabled", "false") 没用。 主机有60G内存。大约 30G 用于 Spark/Yarn。我不确定我的工作需要多少堆大小,但同时没有太多其他进程在进行。尤其是地图只有 70MB 左右。

一些与广播相关的代码:

val mappingAllLocal: Map[String, Int] = mappingAll.rdd.map(r => (r.getAs[String](0), r.getAs[Int](1))).collectAsMap().toMap
// I can use the above mappingAll to HDFS, and it's around 70MB
val mappingAllBrd = sc.broadcast(mappingAllLocal) // <-- this is where the out of memory happens

【问题讨论】:

堆大小和您可能设置的其他参数是多少?你能解释一下吗?顺便说一句,您如何提交工作?还有一些你遇到问题的代码? @ChikuMiku 谢谢!我刚刚用更多信息编辑了我的问题。 你在提交纱线吗?如果是,那么您有多少 DN,您的容器的最大尺寸是多少? 【参考方案1】:

使用set("spark.driver.memory", "15G") 对客户端模式没有影响。提交申请时必须使用命令行参数--conf="spark.driver.memory=15G"来增加驱动的堆大小。

【讨论】:

非常感谢!有用!您如何发现 set("spark.driver.memory", "15G") 对客户端模式没有影响?是否有任何其他设置对客户端模式没有影响?谢谢! Spark's documents中提到过【参考方案2】:

您可以尝试增加 JVM 堆大小:

-Xmx2g : max size of 2Go
-Xms2g : initial size of 2Go (default size is 256mo)

【讨论】:

谢谢!我没有尝试这个解决方案。我首先尝试了 Dikei 的解决方案,因为它似乎更适合 Spark。

以上是关于Spark:广播对象时内存不足的主要内容,如果未能解决你的问题,请参考以下文章

内存不足错误的 Spark 配置

Apache Spark 内存不足,分区数量较少

对于 Java 内存不足错误,我应该增加哪种类型的 Spark 内存?

由于内存不足,Spark Join 失败

Spark 流式接收器内存不足 (OOM)

在 takeSample 上 Spark 作业的堆内存不足