spark.sql.shuffle.partitions的最佳值应该是什么,或者在使用Spark SQL时如何增加分区?

时间:2015-09-02 09:35:21

标签: apache-spark apache-spark-sql

您好我正在使用Spark SQL hiveContext.sql(),它使用group by queries并且我遇到了OOM个问题。因此,考虑将spark.sql.shuffle.partitions的值从200默认增加到1000,但它没有帮助。请纠正我,如果我错了,这个分区将共享数据随机加载,因此分区更少数据保持。请指导我是Spark新手。我正在使用Spark 1.4.0,我有大约1TB的未压缩数据,可以通过查询使用hiveContext.sql()组进行处理。

4 个答案:

答案 0 :(得分:46)

如果随机播放内存不足,请尝试将spark.sql.shuffle.partitions设置为2001。

Spark uses a different data structure for shuffle book-keeping when the number of partitions is greater than 2000:

private[spark] object MapStatus {

  def apply(loc: BlockManagerId, uncompressedSizes: Array[Long]): MapStatus = {
    if (uncompressedSizes.length > 2000) {
      HighlyCompressedMapStatus(loc, uncompressedSizes)
    } else {
      new CompressedMapStatus(loc, uncompressedSizes)
    }
  }
...

我真的希望他们能让你独立配置它。

顺便说一下,我找到了this information in a Cloudera slide deck

答案 1 :(得分:9)

好的,所以我认为你的问题更为笼统。它不是特定于Spark SQL,它是Spark的一个普遍问题,它忽略了文件很少时你告诉它的分区数量。除非您致电repartition,否则Spark似乎与HDFS上的文件数具有相同数量的分区。因此,调用repartition应该可行,但需要注意不必要地进行随机播放。

我刚才提出这个问题,还没有得到一个好的答案:(

Spark: increase number of partitions without causing a shuffle?

答案 2 :(得分:4)

它实际上取决于您的数据和查询,如果Spark必须加载1Tb,那么您的设计就会出现问题。

使用superbe Web UI查看DAG,表示Spark如何将SQL查询转换为作业/阶段和任务。

有用的指标是"输入"和" Shuffle"。

  • 对数据进行分区(Hive /目录布局,如/ year = X / month = X)
  • 使用spark CLUSTER BY功能来处理每个数据分区
  • 使用ORC / Parquet文件格式,因为它们提供"下推过滤器",无用数据未加载到Spark
  • 分析Spark历史以了解Spark如何读取数据

另外,OOM可能发生在您的驱动程序上?

- >这是另一个问题,驱动程序将在最后收集您想要的数据。如果你要求太多数据,驱动程序将会OOM,尝试限制你的查询,或写另一个表(Spark语法CREATE TABLE ...AS)。

答案 3 :(得分:0)

我从Cloudera遇到了关于Hive Partitioning的this post。查看“指针”部分,了解每个分区中的分区数和文件数导致名称节点过载,这可能会导致OOM。