同时对Hive表进行分区和分区的好处是什么? 我有一张桌子"订单"其中包含1M条记录,但记录来自6个特定城市。 现在,如果我只根据城市打包我的表订单,我的仓库目录(在Hive中)会得到6个不同的文件夹,每个文件夹对应一个特定的城市和数据。
当我分区然后将我的表 Orders 分区时,我仍然可以在hive下的仓库目录中看到相同的6个文件夹。我尝试使用16个桶,但仍然,数据的文件夹按城市划分。 以下是代码:
create table Orders ( id int, name string, address string)
partitioned by (city string)
clustered by (id) into 16 buckets
row format delimited fields terminated by ','
stored as TEXTFILE
有人可以概述为什么Hive的表现如此。 此外,我运行了一些性能指标,如计数和分组。我没有发现分区的分段表格有任何重大改进,只有分段或仅分区。
谢谢。
我在12个内核上运行Hadoop,在8个集群上运行36 Gb RAM。
答案 0 :(得分:6)
分区和分段是在物理层分割数据的两种不同类型。
如您所见,当您按列对表进行分区时,将为该列的每个值创建一个目录。因此,您通常希望对具有低基数的列进行分区。您将看到的最常见的分区列之一是date
。
通过分段,列值被散列为固定数量的桶。这也会物理拆分您的数据。在您的情况下,如果您检查city
目录中的文件,您将看到16个文件,每个桶1个。 Bucketing通常用于高基数列。
那么,分区和分组的优势是什么?由于数据在物理上是分区的,因此查询层可以应用两种类型的优化,称为分区修剪和桶修剪。当应用WHERE
子句时,这些优化将启动,允许优化器应用修剪策略。例如,在您的情况下,您有6个目录(城市)乘以16个文件(ID存储桶),因此您的表中总共有96个文件。如果为city = "city1"
包含where子句,那么只会扫描16个文件,因为分区修剪会启动。如果你使用了id = 10101
的where子句,那么自从修剪桶以来只会扫描6个文件可以应用。如果您同时应用城市过滤器和ID过滤器,则只需要扫描1个文件。
修改强> 正如评论中所指出的,铲斗修剪仅在Tez引擎中实现。因此,虽然理论上可以修剪存储桶,但Hive MR中尚未实现优化。