美文网首页
Spark 内存调优

Spark 内存调优

作者: scottzcw | 来源:发表于2018-08-28 22:22 被阅读31次

JVM堆内存分为一块较大的Eden和两块较小的Survivor,每次只使用Eden和其中一块Survivor,当回收时将Eden和Survivor中还存活着的对象一次性复制到另外一块Survivor上,最后清理掉Eden和刚才用过的Survivor。也就是说当task创建出来对象会首先往Eden和survivor1中存放,survivor2是空闲的,当Eden和survivor1区域放满以后就会触发minor gc小型垃圾回收,清理掉不再使用的对象。会将存活下来的对象放入survivor2中。

如果存活下来的对象大小大于survivor2的大小,那么JVM就会将多余的对象直接放入到老年代中。

如果这个时候年轻代的内存不是很大的话,就会经常的进行minor gc,频繁的minor gc会导致短时间内有些存活的对象(多次垃圾回收都没有回收掉,一直在用的又不能被释放,这种对象每经过一次minor gc都存活下来)频繁的倒来倒去,会导致这些短生命周期的对象(不一定长期使用)每进行一次垃圾回收就会长一岁。年龄过大,默认15岁,垃圾回收还是没有回收回去就会跑到老年代里面去了。

这样会导致在老年代中存放大量的短生命周期的对象,老年代应该存放的是数量比较少并且会长期使用的对象,比如数据库连接池对象。这样的话,老年代就会满溢(full gc 因为本来老年代中的对象很少,很少进行full gc 因此采取了不太复杂但是消耗性能和时间的垃圾回收算法)。不管minor gc 还是 full gc都会导致JVM的工作线程停止。

总结:

堆内存不足造成的影响:

1)频繁的minor gc。

2)老年代中大量的短生命周期的对象会导致full gc。

3) gc 多了就会影响Spark的性能和运行的速度。

Spark  JVM调优主要是降低gc时间,可以修改Executor内存的比例参数。

RDD缓存、task定义运行的算子函数,可能会创建很多对象,这样会占用大量的堆内存。堆内存满了之后会频繁的GC,如果GC还不能够满足内存的需要的话就会报OOM。比如一个task在运行的时候会创建N个对象,这些对象首先要放入到JVM年轻代中。比如在存数据的时候我们使用了foreach来将数据写入到内存,每条数据都会封装到一个对象中存入数据库中,那么有多少条数据就会在JVM中创建多少个对象。

Spark中如何内存调优?

Spark Executor堆内存中存放(以静态内存管理为例):RDD的缓存数据和广播变量(spark.storage.memoryFraction 0.6),shuffle聚合内存(spark.shuffle.memoryFraction 0.2),task的运行(0.2)那么如何调优呢?

1)提高Executor总体内存的大小

2)降低储存内存比例或者降低聚合内存比例

如何查看gc?

Spark WEBUI中job->stage->task

Executor的堆外内存

原因:

Spark底层shuffle的传输方式是使用netty传输,netty在进行网络传输的过程会申请堆外内存(netty是零拷贝),所以使用了堆外内存。默认情况下,这个堆外内存上限默认是每一个executor的内存大小的10%;真正处理大数据的时候,这里都会出现问题,导致spark作业反复崩溃,无法运行;此时就会去调节这个参数,到至少1G(1024M),甚至说2G、4G。

executor在进行shuffle write,优先从自己本地关联的mapOutPutWorker中获取某份数据,如果本地block manager没有的话,那么会通过TransferService,去远程连接其他节点上executor的block manager去获取,尝试建立远程的网络连接,并且去拉取数据。频繁创建对象让JVM堆内存满溢,进行垃圾回收。正好碰到那个exeuctor的JVM在垃圾回收。处于垃圾回过程中,所有的工作线程全部停止;相当于只要一旦进行垃圾回收,spark / executor停止工作,无法提供响应,spark默认的网络连接的超时时长是60s;如果卡住60s都无法建立连接的话,那么这个task就失败了task失败了就会出现shuffle file cannot find的错误。

解决方法:

1.调节等待时长。

在./spark-submit提交任务的脚本里面添加:

--conf spark.core.connection.ack.wait.timeout=300

Executor由于内存不足或者堆外内存不足了,挂掉了,对应的Executor上面的block manager也挂掉了,找不到对应的shuffle map output文件,Reducer端不能够拉取数据。

2.调节堆外内存大小

在./spark-submit提交任务的脚本里面添加

yarn下:

--conf  spark.yarn.executor.memoryOverhead=2048 单位M

standalone下:

--conf  spark.executor.memoryOverhead=2048单位M

相关文章

  • Spark 内存调优

    JVM堆内存分为一块较大的Eden和两块较小的Survivor,每次只使用Eden和其中一块Survivor,当回...

  • Spark性能调优

    《Spark性能优化:开发调优篇》《Spark性能优化:资源调优篇》《Spark性能优化:数据倾斜调优》《Spar...

  • Spark性能优化:数据倾斜调优(转)

    《Spark性能优化:开发调优篇》《Spark性能优化:资源调优篇》《Spark性能优化:数据倾斜调优》《Spar...

  • Spark性能优化:开发调优篇(转)

    《Spark性能优化:开发调优篇》《Spark性能优化:资源调优篇》《Spark性能优化:数据倾斜调优》《Spar...

  • Spark性能优化:资源调优篇(转)

    《Spark性能优化:开发调优篇》《Spark性能优化:资源调优篇》《Spark性能优化:数据倾斜调优》《Spar...

  • 2019-03-13-Spark官方调优文档翻译

    Spark调优 由于大部分Spark计算都是在内存中完成的,所以Spark程序的瓶颈可能由集群中任意一种资源导致,...

  • Spark 性能调优

    1 Spark SQL性能调优 通过缓存数据、调优参数、增加并行度提升性能P941)缓存数据构建一个内存中的列格式...

  • Spark 调优

    大家都知道spark的计算是基于内存的,所以内存的合理使用对spark调优至关重要,其实大方向主要关注三个方面CP...

  • JVM-GC调优

    零、本文纲要 一、 GC调优基本思路二、 新生代内存调优三、 老年代内存调优四、 GC调优案例 官方GC调优指南[...

  • Spark性能优化-开发调优

    Spark性能优化分为四个方面: 1、开发调优2、资源调优3、数据倾斜调优4、shuffle调优 1. 开发调优 ...

网友评论

      本文标题:Spark 内存调优

      本文链接:https://www.haomeiwen.com/subject/baqliftx.html