前言
Apache Hive是 Hadoop 生态系统中不可或缺的数据仓库工具,它提供了类 SQL 的查询语言(HiveQL),让数据分析师和工程师能够轻松地对存储在 HDFS 上的大规模数据进行处理和分析。
在 Hive 中,表是最核心的概念之一。本文将详细介绍 Hive 的四种主要表类型:内部表、外部表、分区表和分桶表,帮助你全面掌握 Hive 表的原理与使用。
────────────────────────────────────────
一、内部表(Managed Table)
什么是内部表?
内部表是 Hive 的默认表类型,它的元数据(存储在 MySQL 中)和数据文件(存储在 HDFS 上)完全由 Hive 自身管理。
创建内部表
CREATE TABLE student (
id INT,
name STRING,
age INT
)
ROW FORMAT DELIMITED FIELDS TERMINATED BY ',';
核心特性
- • 内部表完全由 Hive 管理(元数据 + 数据文件)
- • 使用 LOAD DATA 加载数据时,数据文件会被移动到 Hive 仓库目录
- • 删除内部表时,元数据和数据文件都会被删除
二、外部表(External Table)
什么是外部表?
外部表允许 Hive 访问存储在 HDFS 上但不属于 Hive 仓库目录的数据。外部表的元数据由 Hive 管理,而数据文件则由 HDFS 管理。
创建外部表
CREATE EXTERNAL TABLE external_student (
id INT,
name STRING,
age INT
)
ROW FORMAT DELIMITED FIELDS TERMINATED BY ','
LOCATION '/user/data/student';
核心特性
- • 元数据由 Hive 管理,数据文件由 HDFS 管理
- • 删除外部表时,只删除元数据,数据文件仍然保留
- • 数据更加安全,不会因误删表而导致数据丢失
三、内部表 vs 外部表(面试高频题 🔥)
对比维度 | 内部表(Managed Table) | 外部表(External Table) |
管理范围 | 元数据 + 数据文件完全由 Hive 管理 | 元数据由 Hive 管理,数据由 HDFS 管理 |
创建语法 | CREATE TABLE(默认) | CREATE EXTERNAL TABLE |
删除行为 | 删除元数据 + 数据文件 | 只删除元数据,数据文件保留 |
数据安全性 | 相对较低 | 相对较高(误删可恢复数据) |
适用场景 | 临时表、测试数据、ETL 中间表 | 数据来自外部、共享数据、原始数据保护 |
💡 拓展思考:内部表和外部表的相互转换
-- 内部表 → 外部表
ALTER TABLE table_name SET TBLPROPERTIES('EXTERNAL'='TRUE');
-- 外部表 → 内部表
ALTER TABLE table_name SET TBLPROPERTIES('EXTERNAL'='FALSE');
────────────────────────────────────────
四、分区表(Partitioned Table)
什么是分区表?
Hive 分区表是一种优化 Hive 查询的方法,用以提高查询性能。分区表通过将数据分散到不同的分区目录中,使得查询仅扫描目标分区的数据,而不是整个表,从而大大减少了数据扫描的范围。
创建分区表
CREATE TABLE trade (
city STRING,
amt INT
)
PARTITIONED BY (sf STRING)
ROW FORMAT DELIMITED FIELDS TERMINATED BY ',';
添加分区的两种方式
方式一:手动添加分区(ALTER TABLE)
ALTER TABLE trade ADD PARTITION(sf='shandong');
ALTER TABLE trade ADD PARTITION(sf='henan');
方式二:MSCK REPAIR(推荐,常用方式)
先将外部数据文件上传(put)到 Hive 表的对应分区目录中,此时数据还没有元数据信息,然后执行修复命令自动添加元数据:
MSCK REPAIR TABLE trade;
查询分区数据
SELECT * FROM trade WHERE sf='shandong';
五、动态分区表
什么是动态分区?
动态分区允许在插入数据时,根据分区字段的值自动创建对应的分区,无需手动创建每个分区。在数据量较大或分区数量不确定时非常有用。
实现步骤
第①步:创建临时表,存储全部数据
CREATE TABLE city (
province_id STRING,
city_id STRING,
amount INT,
city_name STRING
)
ROW FORMAT DELIMITED FIELDS TERMINATED BY ',';
第②步:上传数据到临时表
第③步:开启 Hive 支持动态分区的参数
SET hive.exec.dynamic.partition=true;
SET hive.exec.dynamic.partition.mode=nonstrict;
第④步:创建分区表
CREATE TABLE city_dtfq (
province_id STRING,
city_id STRING,
amount INT,
city_name STRING
)
PARTITIONED BY (sf STRING);
第⑤步:从临时表导入数据到分区表(自动创建分区)
⚠️ 分区字段必须放在 SELECT 语句的最后!
INSERT INTO city_dtfq PARTITION(sf)
SELECT province_id, city_id, amount, city_name,
province_id -- 该字段的值作为 sf 分区的值(自动创建分区)
FROM city;
六、分桶表(Bucketed Table)
什么是分桶表?
在 Hive 中,对表进行分桶(Bucketing)是一种优化数据查询和数据存储的方法。分桶可以帮助提高某些类型查询的效率,特别是在执行 JOIN 操作时。
分桶通过将数据按照指定列的哈希值分散到多个文件中,每个文件称为一个桶(Bucket),从而使得查询可以更快地定位到需要的数据。
实现步骤
第①步:创建临时表,存储全部数据
CREATE TABLE city (
province_id STRING,
city_id STRING,
amount INT,
city_name STRING
)
ROW FORMAT DELIMITED FIELDS TERMINATED BY ',';
第②步:上传数据到临时表
第③步:创建分桶表(指定分桶字段和桶数量)
CREATE TABLE city_ft (
province_id STRING,
city_id STRING,
amount INT,
city_name STRING
)
CLUSTERED BY (province_id) INTO 2 BUCKETS;
第④步:设置支持分桶的参数
SET hive.enforce.bucketing=true;
第⑤步:从临时表导入数据到分桶表
INSERT INTO city_ft SELECT * FROM city;
七、总结对比
表类型 | 数据管理方式 | 删除时的影响 | 核心用途 |
内部表 | 完全由 Hive 管理 | 元数据和数据文件 | 临时表、测试数据 |
外部表 | 元数据:Hive 管理 | 只删除元数据 | 外部数据源 |
分区表 | 按分区字段 | 按分区粒度删除 | 查询性能优化 |
分桶表 | 按列哈希值 | 分桶数量固定 | JOIN 性能优化 |
────────────────────────────────────────
🌟 面试重点提示
1️⃣内部表 vs 外部表的区别是 Hive 面试中的必问题,一定要熟记!
2️⃣分区表是最常用的查询优化手段,要重点掌握动态分区的使用
3️⃣分桶表常用于 JOIN 优化和抽样查询,了解原理即可
4️⃣实际工作中,外部表 + 分区表配合使用是最常见的组合
──────────────────────────────────────────────────
📚 如果觉得有帮助,欢迎点赞 👍 收藏 ⭐ 关注 🚀
更多大数据技术干货持续更新中...