Parquet 支持的 Hive 表:Impala 中不可查询的数组列

Posted

技术标签:

【中文标题】Parquet 支持的 Hive 表:Impala 中不可查询的数组列【英文标题】:Parquet-backed Hive table: array column not queryable in Impala 【发布时间】:2016-05-15 21:10:34 【问题描述】:

虽然 Impala 比 Hive 快得多,但我们使用 Hive 是因为它支持复杂(嵌套)数据类型,例如数组和映射。

我注意到,从 CDH5.5 开始,Impala 现在支持复杂的数据类型。由于也可以在 Impala 中运行 Hive UDF,我们可能可以在 Impala 中做任何我们想做的事情,但是要快得多。这是个好消息!

当我浏览文档时,我发现 Impala 希望数据以 Parquet 格式存储。我的原始数据恰好是两列 CSV,其中第一列是 ID,第二列是用竖线分隔的字符串数组,例如:

123,ASDFG|SDFGH|DFGHJ|FGHJK
234,QWERT|WERTY|ERTYU

已创建 Hive 表:

CREATE TABLE `id_member_of`(
  `id` INT, 
  `member_of` ARRAY<STRING>)
ROW FORMAT DELIMITED 
  FIELDS TERMINATED BY ',' 
  COLLECTION ITEMS TERMINATED BY '|' 
  LINES TERMINATED BY '\n' 
STORED AS INPUTFORMAT 
  'org.apache.hadoop.mapred.TextInputFormat' 
OUTPUTFORMAT 
  'org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat';

原始数据已加载到 Hive 表中:

LOAD DATA LOCAL INPATH 'raw_data.csv' INTO TABLE id_member_of;

创建了一个 Parquet 版本的表:

CREATE TABLE `id_member_of_parquet` (
 `id` STRING, 
 `member_of` ARRAY<STRING>) 
STORED AS PARQUET;

CSV 支持的表中的数据已插入 Parquet 表:

INSERT INTO id_member_of_parquet SELECT id, member_of FROM id_member_of;

Parquet 表现在可以在 Hive 中查询:

hive> select * from id_member_of_parquet;
123 ["ASDFG","SDFGH","DFGHJ","FGHJK"]
234 ["QWERT","WERTY","ERTYU"]

奇怪的是,当我在 Impala 中查询同一个 Parquet 支持的表时,它不返回数组列:

[hadoop01:21000] > invalidate metadata;
[hadoop01:21000] > select * from id_member_of_parquet;
+-----+
| id  |
+-----+
| 123 |
| 234 |
+-----+

问题:数组列发生了什么?你能看出我做错了什么吗?

【问题讨论】:

【参考方案1】:

结果非常简单:我们可以通过将数组添加到FROM 中来访问数组,例如

Query: select * from id_member_of_parquet, id_member_of_parquet.member_of
+-----+-------+
| id  | item  |
+-----+-------+
| 123 | ASDFG |
| 123 | SDFGH |
| 123 | DFGHJ |
| 123 | FGHJK |
| 234 | QWERT |
| 234 | WERTY |
| 234 | ERTYU |
+-----+-------+

【讨论】:

是否可以像在 Hive 中那样将数组的内容保留在一行中,而不是按照 ***.com/questions/38711201/… 将数组转换为字符串? @NeilBest 如果你使用 GROUP_CONCAT 是可能的。

以上是关于Parquet 支持的 Hive 表:Impala 中不可查询的数组列的主要内容,如果未能解决你的问题,请参考以下文章

hive 存储格式对比

在 CDH 集群之间复制 parquet 表

为 impala 表无缝覆盖底层 parquet 数据

使用 Java 将 Json 对象转换为 Parquet 格式而不转换为 AVRO(不使用 Spark、Hive、Pig、Impala)

Impala与Hive混合使用的一个深坑

Parquet 格式文件