hadoop—物理内存的使用量在不断增加,以便在yarn上使用spark应用程序

6qfn3psc  于 2021-06-02  发布在  Hadoop
关注(0)|答案(1)|浏览(393)

我在yarn客户机模式下运行一个spark应用程序,它有六个执行器(每个四核,执行器内存=6gb,开销=4gb,spark版本:1.6.3/2.1.0)。
我发现我的执行器内存一直在增加,直到被节点管理器杀死;它给出的信息告诉我 spark.yarn.excutor.memoryOverhead .
我知道这个参数主要控制堆外分配的内存大小。但我不知道Spark发动机什么时候,怎样使用这部分记忆。同时,增加这部分记忆并不总能解决我的问题。有时有效有时无效。当输入数据很大时,它就变得无用了。
仅供参考,我的应用程序的逻辑非常简单。它意味着将一天(一天一个目录)生成的小文件合并成一个文件,并写回hdfs。核心代码如下:

val df = spark.read.parquet(originpath)
              .filter(s"m = ${ts.month} AND d = ${ts.day}")
              .coalesce(400)
val dropDF = df.drop("hh").drop("mm").drop("mode").drop("y").drop("m").drop("d")

dropDF.repartition(1).write
      .mode(SaveMode.ErrorIfExists)
      .parquet(targetpath)

源文件可能有几百到几千级的分区。Parquet地板的总锉数大约是1到5 国标。
我还发现,在从不同的机器上随机读取数据的步骤中,随机读取的大小大约是输入大小的四倍,这是有线的或者一些我不知道的原理。
不管怎样,我已经为这个问题做了一些调查。一些文章说它在直接缓冲存储器上(我自己没有设置)。
有文章说,人们用更频繁的完全gc来解决这个问题。
另外,我在堆栈上找到一个人 溢出的情况非常相似:在yarn中不断增加spark应用程序的物理内存
这家伙声称这是一个错误的Parquet地板,但一个评论质疑他。这个邮件列表中的人也可能在几个小时前收到一封来自blondowski的电子邮件,他在编写json:executors时描述了这个问题—内存不足
因此,对于不同的输出格式,这似乎是一个常见的问题。
我希望有经验的人能对这个问题作出解释。为什么会发生这种情况?解决这个问题的可靠方法是什么?

izkcnapc

izkcnapc1#

这几天我只是和同事一起做些调查。我的想法是:从spark1.2开始,我们使用netty和堆外内存来减少洗牌和缓存块传输期间的gc。在我的例子中,如果我试图增加足够大的内存开销。我将获得最大直接缓冲区异常。当netty执行块传输时,默认情况下会有五个线程将数据块抓取到目标执行器。在我的情况下,一个块太大,无法放入缓冲区。所以gc在这里帮不上忙。我的最终解决方案是在重新分区(1)之前再进行一次重新分区。只是为了比原来的分区多出10倍。这样,我就可以减少每个块的大小。这样我终于成功了。
我还想说,将一个大数据集重新划分为单个文件不是一个好的选择。这种极不平衡的情况是在浪费您的计算资源。
欢迎评论,我还是不太理解这部分。

相关问题