【问题标题】:Parquet support for 'tinyint' columnsParquet 支持“tinyint”列
【发布时间】:2018-12-20 22:11:54
【问题描述】:

我在使用 AWS Athena 在 S3 上查询镶木地板数据时遇到了这个奇怪的问题。 基本上,我在 S3 上存储了一个 parquet 文件(约 38MB),其架构如下:

表名:test_table_tinyint

  • ntwk_id (int)
  • broadcast_date(字符串)
  • daypart_id (tinyint)

然后我运行以下查询: SELECT count(*) FROM "test_table_tinyint" where daypart_id = 5;

结果: 运行时间:2.7 秒,扫描数据:32MB

这很奇怪,因为它看起来不是利用 parquet 文件中的列索引,而是实际上进行了全表扫描。

然后作为比较,我创建了另一个具有相同数据但架构略有不同的表:

表名:test_table_int

  • ntwk_id (int)
  • broadcast_date(字符串)
  • daypart_id (int)

SELECT count(*) FROM "test_table_int" where daypart_id = 5;

这次我得到了更好的结果:

运行时间:1.07 秒,扫描数据:326.49KB

我在使用 Spark SQL 的 Spark 中遇到了类似的问题,看起来 parquet 文件中的 TinyInt 列会导致全表扫描。如果我将文件转换为 ORC 格式,那么 AWS Athena 和 Spark SQL 都会得到与 'TinyInt' 和 'Int' 相似的结果

有什么想法吗?

谢谢

【问题讨论】:

  • 这很可能与强制有关,daypart_id = 5 实际上是CAST(daypart_id AS INTEGER) = 5。您可以尝试通过为常量指定显式类型来解决此问题:daypart_id = TINYINT '5'
  • 谢谢,@PiotrFindeisen 使用显式类型有效。
  • 我很高兴听到这个消息。我将我的评论转化为答案。

标签: amazon-web-services apache-spark-sql parquet amazon-athena presto


【解决方案1】:

这是因为当daypart_id 是TINYINT 时,daypart_id = 5 实际上是CAST(daypart_id AS INTEGER) = 5(强制是从窄到宽的类型)。

为了防止强制发生和混淆下推,您可以提供5 常量和显式类型:daypart_id = TINYINT '5'

注意:我几乎可以肯定 Presto 的较新版本已修复此问题,因此您无需更改查询。您可以很容易地在 AWS 上使用更新的 Presto 版本,而不是无服务器。

【讨论】:

    猜你喜欢
    • 2018-12-14
    • 1970-01-01
    • 2020-06-19
    • 1970-01-01
    • 2016-09-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多