今天是来自新浪的面试题:Hive为什么要做分区,Hive的元数据存在哪?
问题分析
考官主要考核你对Hive开发中分区和元数据存储的理解,因此需要讲出自己对他们的理解即可。
核心问题回答
分区:Hive在执行查询时,一般会扫描整个表的数据,由于表的数据量大,全表扫描消耗的时间长、效率低。
而有时,查询只需要扫描表中的一部分数据即可,Hive引入了分区表的概念,将表的数据存储在不同的子目录中,每一个子目录对应一个分区,只查询部分分区数据时,可避免全表扫描,从而提高查询效率。
元数据存储:Hive将元数据存储在关系型数据库中(如MySQL、derby),Hive的元数据包括数据库名、表名及类型、字段名称及数据类型、数据所存储的位置等。
Hive的元数据默认存储在自带的derby数据库中,但是derby数据库是由java语言开发的,占用资源少、单进程、单用户,而我们一般均使用MySQL存储Hive元数据。
问题扩展
除了分区表和元数据的存储外,Hive还有分桶表以及内部表、外部表,面试官有可能会从分区的话题上引入到分桶、内部表、外部表的概念、以及分区表与分桶表、内部表与外部表的区别。
分桶:当单个分区或者表的数据量过大时,分区不能更细粒度的划分数据,就需要使用分桶技术将数据划分成更细的粒度,将数据按照指定的字段进行分成多个桶,即将数据按照字段进行划分,数据按照字段划分到多个文件当中。
分区和分桶的区别:
a. 分桶是按照列的哈希值进行划分的,相对比较平均;而分区是按照列的值来进行划分的,容易造成数据倾斜。
b. 分桶是对应不同的文件(细粒度),分区是对应不同的文件夹(粗粒度).分桶是更为细粒度的数据范围划分,分桶的比分区获得更高的查询处理效率,使取样更高效。
c. 普通表(外部表、内部表)、分区表这三个都是对应HDFS上的目录,桶表对应是目录里的文件。
Hive创建表时,可指定表的类型,表的类型有两种,分别为内部表和外部表,两者有如下区别:
创建表:默认情况下,我们创建的是内部表,若是想要创建外部表,则需要使用关键字EXTERNAL;
加载数据:加载数据到内部表,数据则会移动到自己的数据仓库目录下,而加载数据到外部表,数据并没有移动到自己的数据仓库目录下(如果指定了Location),也就是说外部表中的数据并不是由它自己来管理的;
删除表:删除内部表时,表的定义(元数据)和数据会被同时删除,而删除外部表时,仅仅删除表的定义,数据则被保留。
结合项目中使用
若是我们要收集某个大型网站的日志数据,一个网站每天的日志数据存储在同一张表上,并且每天会生成大量的日志,导致数据表的内容巨大,在查询时进行全表扫描耗费的资源非常多。
那其实这个情况下,我们可以按照日期对表进行分区,不同日期的数据存放在不同的分区,在查询时只要指定分区字段的值就可以直接从该分区查找。
推荐阅读:
【每日一题】Kafka零拷贝的原理?(京东)
【每日一题】HBase如何读取数据?(中国人寿)
【每日一题】Zookeeper的选举机制及使用场景(小米)
【每日一题】Redis的热键问题?Redis的数据类型 (京东)