Spark - StorageLevel(DISK_ONLY与MEMORY_AND_DISK)和内存不足的Java堆空间

Mat*_*tek 8 memory caching scala apache-spark rdd

最近我一直在运行一个记忆重的火花工作,并开始怀疑火花的存储水平.我坚持使用我的一个RDD,因为它使用了两次StorageLevel.MEMORY_AND_DISK.我在工作期间获得了OOM Java堆空间.然后,当我完全删除了持久性时,该工作已经成功完成.

我一直认为它MEMORY_AND_DISK基本上是一个完全安全的选项 - 如果你的内存不足,它会将对象溢出到磁盘,完成.但现在它似乎并没有像我预期的那样真正发挥作用.

这导致两个问题:

  1. 如果MEMORY_AND_DISK在执行程序内存不足时将对象溢出到磁盘,使用DISK_ONLY模式是否有意义(除了一些非常具体的配置spark.memory.storageFraction=0)?
  2. 如果MEMORY_AND_DISK在执行程序内存不足时将对象溢出到磁盘,如何通过删除缓存来解决OOM问题?我错过了什么,问题实际上是在其他地方吗?

Mat*_*tek 5

所以,几年后 ;) 这就是我认为发生的事情:

  • 缓存不是一种节省执行内存的方法。您能做的最好的事情是DISK_ONLY在缓存时不要丢失执行内存 ( )。
  • 尽管我不记得实际用例,但很可能是由于缺少执行内存导致我的工作抛出 OOM 错误。
  • 我使用了MEMORY_AND_DISK缓存,这MEMORY部分来自统一区域,这使我的工作无法完成(因为Execution = Unified - Storage内存不足以执行工作)
  • 由于上述原因,当我完全删除缓存时,速度变慢了,但作业有足够的执行内存来完成。
  • 有了DISK_ONLY缓存,工作似乎也能完成(虽然不一定更快)。

https://spark.apache.org/docs/latest/tuning.html#memory-management-overview


bai*_*rek 1

MEMORY_AND_DISK不会“当执行器内存不足时将对象溢出到磁盘”。它告诉 Spark 将不适合内存的分区写入磁盘,以便在需要时从那里加载它们。

处理巨大的数据集时,您绝对应该考虑将数据保存到 DISK_ONLY。 https://spark.apache.org/docs/latest/rdd-programming-guide.html#which-storage-level-to-choose