一、核心架构与特性
- 数据模型:
-
内部表 vs. 外部表:核心区别在于数据生命周期管理。删除内部表会同时删除元数据和 HDFS 上的数据;删除外部表仅删除元数据,HDFS 数据保留。外部表常用于多系统共享数据。
-
分区:根据某列(如
dt=20240326)将数据分到不同目录,显著提升查询效率(避免全表扫描)。 -
分桶:根据哈希函数将数据分成多个文件,优化 JOIN 查询、数据采样,并可与分区结合。
- 存储与压缩:
-
文件格式:
-
TextFile:默认,可读性强,但压缩比和查询效率低。
-
ORC:首选列式存储,支持索引、谓词下推,压缩比和查询性能极高。
create table ... stored as orc。 -
Parquet:另一种流行的列式存储,特别适用于 Spark 生态。
-
-
压缩:可配置表级或输出压缩(如 Snappy, Gzip, LZO)。减少存储和 I/O,但会增加 CPU 开销。
- 计算引擎:
- 默认引擎是 MapReduce,但可切换为 Tez(优化 DAG 执行,减少中间落地)或 Spark(内存计算,更快)。
二、HiveQL 要点与优化
- 查询优化 - 核心思想:
-
谓词下推:尽早过滤数据,减少后续处理量。ORC/Parquet 格式支持更佳。
-
Map端 JOIN:当一张小表可装入内存时,可启动 Map 端 JOIN 避免 Reduce 阶段。通过
set hive.auto.convert.join=true;启用。 -
倾斜数据 JOIN 优化:
-
set hive.optimize.skewjoin=true;处理 JOIN 键倾斜。 -
set hive.groupby.skewindata=true;处理 GROUP BY 数据倾斜。
-
- 常用函数与技巧:
-
窗口函数:
ROW_NUMBER(),RANK(),DENSE_RANK(),SUM() OVER(PARTITION BY ... ORDER BY ...)等,用于复杂分组聚合和排名。 -
炸裂函数:
EXPLODE()和LATERAL VIEW结合,将数组或 Map 列展开为多行。 -
多维聚合:
GROUPING SETS,CUBE,ROLLUP实现多维度聚合。
- 数据操作:
-
加载数据:
LOAD DATA [LOCAL] INPATH '...' [OVERWRITE] INTO TABLE ...。 -
插入数据:
INSERT OVERWRITE/INTO TABLE ... SELECT ...。 -
动态分区插入:
set hive.exec.dynamic.partition.mode=nonstrict;后,INSERT 时可自动根据 SELECT 列创建分区。
三、重要配置与调优参数
- 动态分区:
-
hive.exec.dynamic.partition=true -
hive.exec.dynamic.partition.mode=nonstrict(允许所有分区列为动态) -
hive.exec.max.dynamic.partitions(控制最大动态分区数)
- 并行执行与压缩:
-
set hive.exec.parallel=true;(开启阶段并行) -
set mapreduce.map.output.compress=true;(Map 输出压缩) -
set hive.exec.compress.output=true;(最终输出压缩)
- 控制 Reduce 数量:
-
通过
mapreduce.job.reduces直接设置。 -
或由
hive.exec.reducers.bytes.per.reducer(每个 Reduce 处理的数据量)间接控制。
四、Hive 执行过程与底层
-
SQL 转换流程:HiveQL → **AST(抽象语法树)** → Query Block → 逻辑执行计划 → 优化 → 物理执行计划 → 编译为 MapReduce/Tez/Spark DAG → 提交到集群执行。
-
元数据存储:表结构、分区信息等存储在元数据库(如 MySQL)中,而实际数据存储在 HDFS 上。
-
SerDe:序列化/反序列化器,定义了如何将 HDFS 数据行解析为 Hive 表记录(如
ROW FORMAT SERDE)。
五、常见问题与排查
-
数据倾斜:表现为某个 Reduce 任务耗时极长。解决方法见上述“倾斜优化”。
-
小文件过多:会压垮 NameNode 并降低查询效率。解决方法:
-
合并:
INSERT OVERWRITE TABLE ... SELECT * FROM ...。 -
配置合并:
hive.merge.mapfiles,hive.merge.mapredfiles。 -
使用
distribute by或cluster by控制输出文件数。
- Debug 与日志:
-
通过
EXPLAIN [EXTENDED]查看执行计划。 -
查看 YARN 任务日志定位失败原因。
总结
掌握 Hive 的关键在于理解其 **“SQL on Hadoop”** 的本质,核心围绕 “分区、分桶、索引、列式存储” 进行性能优化,并熟练运用 窗口函数、JOIN 优化、动态分区 等高级功能来应对实际的大数据分析场景。同时,时刻注意其与关系型数据库在实时性、事务支持上的差异(虽然 Hive 有 LLAP 和事务表,但传统上用于批处理)。