【问题标题】:Use directories for partition pruning in Spark SQL在 Spark SQL 中使用目录进行分区修剪
【发布时间】:2015-07-24 14:24:23
【问题描述】:

我有数据文件(本例中为 json,但也可以是 avro),其目录结构如下:

dataroot
+-- year=2015
    +-- month=06
        +-- day=01
            +-- data1.json
            +-- data2.json
            +-- data3.json
        +-- day=02
            +-- data1.json
            +-- data2.json
            +-- data3.json
    +-- month=07
        +-- day=20
            +-- data1.json
            +-- data2.json
            +-- data3.json
        +-- day=21
            +-- data1.json
            +-- data2.json
            +-- data3.json
        +-- day=22
            +-- data1.json
            +-- data2.json

使用 spark-sql 创建一个临时表:

CREATE TEMPORARY TABLE dataTable
USING org.apache.spark.sql.json
OPTIONS (
  path "dataroot/*"
)

查询表效果很好,但我目前无法使用目录进行修剪。

有没有办法将目录结构注册为分区(不使用 Hive)以避免在查询时扫描整个树?假设我想比较每个月的第一天的数据,并且只读取这些天的目录。

使用 Apache Drill,我可以在查询期间使用目录作为谓词,使用 dir0 等。是否可以使用 Spark SQL 做类似的事情?

【问题讨论】:

  • 你能解决这个问题吗?
  • 不,在提出问题的时候没有,从那以后我没有调查过这个具体案例。

标签: apache-spark apache-spark-sql apache-drill


【解决方案1】:

据我所知,分区自动发现仅适用于 SparkSQL 中的 parquet 文件。见http://spark.apache.org/docs/latest/sql-programming-guide.html#partition-discovery

【讨论】:

  • 虽然 parquet 文件读取确实支持发现类似 Hive 的分区。根据我的经验,数据目录不会作为分区加载。即,当您查询分区键时,您仍在扫描整个树(即,不修剪 - 不是询问者想要的)。
  • @jack 它使用分区跳过而不是读取目录(同样仅适用于镶木地板文件)
  • 自从那条评论之后,我实际上学到了更多。因此,您可以从可用分区中获得优化,但仅限于使用 DataFrames API 时。如果您转换为 RDD(或者甚至在使用 Datasets API 时,据我所知),它总是会读取所有目录,即使它不是必须的。 IOW,你说的是准确的,但仅在使用 DataFrame API 时。
  • 现在可以在 Spark 中基于文本文件的表上进行分区修剪吗?
【解决方案2】:

使用EXPLAIN 查看物理计划,以便扫描哪个文件夹。

另外,您可以在创建表时描述分区,以便 Spark 可以使用它。

我不确定 Spark 1.6 是否正确使用了分区修剪,将 spark.sql.hive.convertMetastoreParquet 设置为 false,我可以看到它但设置为 true(默认),我可以看到 Spark 将扫描所有分区(但这根本不影响性能) .

【讨论】:

  • 每个问题都是不同的,但是在不同的问题设置上翻转该开关会有所帮助。恕我直言,总是值得一试。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2016-09-07
  • 2017-02-15
  • 2020-03-07
  • 2011-01-18
  • 1970-01-01
  • 2017-07-26
  • 2020-01-28
相关资源
最近更新 更多