杀疯了!Hive 高频核心函数全解析:Map/Struct/Array/ 日期 / 字符串 / 聚合一网打尽
作为大数据开发、数仓工程师的必备技能,Hive 函数是处理复杂数据、实现高效查询的核心武器!本文整理了企业级开发中最常用、最核心的 Hive 函数,覆盖复杂数据类型(Array/Map/Struct)、日期函数、字符串函数、类型转换、数学函数、条件判断、行列转换、JSON/URL 解析等全场景,附实战案例 + 语法详解,新手也能直接上手,建议收藏!
一、Hive 复杂数据类型函数(Array/Map/Struct)
工作中常遇到嵌套 / 数组数据,Array、Map、Struct是 Hive 三大复杂类型,配套函数直接解决嵌套数据查询、行列转换、数据解析难题。
1. Array 类型核心操作(高频!)
Array 是有序集合 / 数组,适合存储同类型、有序、可重复的数据(如标签列表、爱好列表、成绩列表),是数仓最常用的复杂类型!
建表语法
create table array1(
name string,
hobbies array<string> -- 字符串数组:爱好列表
)
row format delimited
fields terminated by "\t" -- 字段分隔符
collection items terminated by ","; -- 数组元素分隔符
核心函数 & 用法(最全整理)
| 函数 / 语法 | 作用 | 实战案例 | |
|---|---|---|---|
array[index] |
根据下标取数组元素(下标从 0 开始) | hobbies[0] 取第一个爱好 |
|
size(array) |
获取数组长度 / 元素个数 | size(hobbies) |
|
explode(array) |
行转列,炸开数组为多行 | lateral view explode(hobbies) t as hobby |
|
posexplode(array) |
炸开数组 + 返回下标 | 带位置索引展开 | |
array_contains(array, value) |
判断数组是否包含某个值 | array_contains(hobbies,'篮球') |
|
sort_array(array) |
数组排序(升序) | sort_array(hobbies) |
|
collect_list(col) |
列转行,聚合重复数据为数组 | collect_list(hobby) |
|
collect_set(col) |
列转行,聚合去重数据为数组 | collect_set(hobby) |
|
concat_ws(sep, array) |
数组转字符串(指定分隔符) | `concat_ws(' | |
split(str, sep) |
字符串转数组 | split('篮球,游戏', ',') |
经典实战(必背)
-- 1. 根据下标取数组元素(取第一个爱好)
select name, hobbies[0] from array1;
-- 2. 获取数组长度(统计每个人爱好数量)
select name, size(hobbies) as hobby_cnt from array1;
-- 3. 判断数组是否包含指定值(筛选喜欢篮球的人)
select name from array1 where array_contains(hobbies, '篮球');
-- 4. 行转列:炸开数组(一人多行,每行一个爱好)
select name, hobby from array1
lateral view explode(hobbies) t as hobby;
-- 5. 炸开数组+下标(带位置展开)
select name, pos, hobby from array1
lateral view posexplode(hobbies) t as pos, hobby;
-- 6. 数组排序
select name, sort_array(hobbies) from array1;
-- 7. 列转行:多行转数组(去重)
select name, collect_set(hobby) from 表 group by name;
-- 8. 数组 ↔ 字符串互转
-- 数组转字符串(用逗号拼接)
select name, concat_ws(',', hobbies) from array1;
-- 字符串转数组
select split('足球,游戏,读书', ',');
2. Map 类型核心操作
Map 是键值对(key-value) 结构,适合存储动态属性数据(如学生各科成绩)。
建表语法
create table map1(
name string,
scores map<string,int> -- key为字符串(科目),value为整型(分数)
)
row format delimited
fields terminated by "\t" -- 字段分隔符
collection items terminated by "," -- Map元素分隔符
map keys terminated by ":"; -- Map键值分隔符
核心函数 & 用法
| 函数 / 语法 | 作用 | 实战案例 |
|---|---|---|
map['key'] |
获取 Map 中指定 key 的 value | select scores['math'] from map1; |
explode(map) |
行转列,炸开 Map 为多行 | lateral view explode(scores) t as c,s |
collect_list() |
聚合多行数据为列表 | collect_list(concat(c,":",s)) |
concat_ws() |
指定分隔符拼接字符串 | concat_ws(",", 列表) |
str_to_map() |
字符串转回 Map 集合 | str_to_map(拼接字符串) |
经典实战
-- 1. 查询数学>35分的学生英语、自然成绩
select name,scores['english'],scores['nature'] from map1 where scores['math']>35;
-- 2. 行转列:炸开Map所有科目+成绩
select name,c,s from map1 lateral view explode(scores) mytable as c,s ;
-- 3. 聚合:字符串→列表→字符串→Map
select name,str_to_map(concat_ws(",",collect_list(concat(c,":",s))))
from map1 lateral view explode(scores) mytable as c,s group by name;
3. Struct 类型核心操作
Struct 是结构体,固定字段(类似 Java 对象),适合存储固定属性数据
建表语法
create table struct1(
name string,
score struct<chines:int,math:int,english:int,nature:int> -- 固定字段
)
row format delimited
fields terminated by "\t"
collection items terminated by ",";
核心函数和用法
| 函数 / 语法 | 作用 | 实战案例 |
|---|---|---|
struct.字段名 |
获取结构体指定字段值 | select score.math from struct1; |
split(字符串, 分隔符) |
字符串切割为数组 | split(scores,",") |
cast(值 as 类型) |
数据类型强制转换 | cast(score as int) |
explode() |
炸开数组为多行 | lateral view explode(数组) t as score |
经典实战
-- 1. 查询数学>35分的学生英语、语文成绩
select name,score.chines,score.english from struct1 where score.math > 35;
-- 2. 字符串切割+行转列+求和(求学生总成绩)
select name, sum(cast(score as int))
from struct2 lateral view explode(split(scores,",")) mytable as score
group by name;
二、Hive 日期函数(高频!数仓必用)
数仓开发中时间筛选、时间计算、格式转换全靠它,是使用频率最高的函数组。
| 函数 | 作用 | 案例 |
|---|---|---|
current_date() |
获取当前系统日期(yyyy-MM-dd) | select current_date(); |
current_timestamp() |
获取当前时间戳(yyyy-MM-dd HH:mm:ss) | select current_timestamp(); |
unix_timestamp() |
获取当前时间戳(秒级数字) | select unix_timestamp(); |
unix_timestamp(时间字符串, 原格式) |
指定格式时间→时间戳 | unix_timestamp('2017/2/1','yyyy/MM/dd') |
from_unixtime(时间戳, 目标格式) |
时间戳→指定格式日期字符串 | from_unixtime(123456,'yyyy/MM/dd') |
datediff(结束日期, 开始日期) |
计算两个日期天数差 | datediff('2025-11-20',current_date()) |
months_between(日期1, 日期2) |
计算两个日期月份差 | months_between('2025-11-20',current_date()) |
date_add(日期, 天数) |
日期加天数 | date_add(current_date(),20) |
date_sub(日期, 天数) |
日期减天数 | date_sub(current_date(),141) |
add_months(日期, 月数) |
日期加月份 | add_months(current_date(),1) |
last_day(日期) |
获取当月最后一天 | last_day(current_date()) |
dayofmonth(日期) |
获取日期是当月第几天 | dayofmonth(current_date()) |
date_format(日期, 目标格式) |
日期格式化 | date_format(current_date(),'yyyy/MM/dd') |
高频实用场景
-- 1. 获取下个月第一天
select date_add(last_day(current_date()),1);
-- 2. 获取当月第一天
select date_sub(current_date(),dayofmonth(current_date())-1);
-- 3. 日期格式转换:2025-11-20 → 2025/11/20
select from_unixtime(unix_timestamp('2025-11-20','yyyy-MM-dd'),'yyyy/MM/dd');
三、Hive 字符串函数(数据清洗必备)
数据清洗、格式拼接、切割、替换的核心工具,处理文本数据离不开它。
| 函数 | 作用 | 案例 |
|---|---|---|
lower(字符串) |
转小写 | lower('ABHNCxxx') |
upper(字符串) |
转大写 | upper('abbbbbajsfaj') |
length(字符串) |
统计字符串长度 | length('lyfclt') |
concat(字符串1,字符串2) |
直接拼接字符串 | concat('l','c') |
concat_ws(分隔符, str1,str2) |
指定分隔符拼接 | concat_ws('-','a','b','c') → a-b-c |
substr(字符串, 起始位, 长度) |
截取子串 | substr('hello',2,2) → el |
replace(字符串, 旧值, 新值) |
字符串替换 | replace('a,c,v',',','*') → a*c*v |
reverse(字符串) |
字符串反转 | reverse("hello") → olleh |
explode(数组) |
炸开数组为多行 | explode(split("a-s-d",'-')) |
posexplode(数组) |
炸开数组 + 返回下标 | posexplode(split('a-n-c','-')) |
四、类型转换 & 数学函数
1. 类型转换函数
| 函数 | 作用 | 案例 |
|---|---|---|
cast(值 as 目标类型) |
强制类型转换 | cast('123' as int)+1 → 124 |
注意:小数转整数会自动向下取整,如 cast(1.6 as int) → 1
2. 数学函数
| 函数 | 作用 | 案例 |
|---|---|---|
round(数字) |
四舍五入 | round(42.8) → 43 |
ceil(数字) |
向上取整 | ceil(34.1) → 35 |
floor(数字) |
向下取整 | floor(34.9) → 34 |
abs(数字) |
求绝对值 | abs(-1) → 1 |
pmod(数字, 模数) |
取模 / 求余数 | pmod(3,2) → 1 |
五、条件判断函数(数据统计必备)
用于数据分组、空值处理、多条件分支,是报表统计的核心函数。
| 函数 | 作用 | 案例 |
|---|---|---|
nvl(值, 默认值) |
空值替换:为 null 返回默认值 | nvl(null,0) → 0 |
if(条件, 成立值, 不成立值) |
单条件判断 | if(1=1,1,2) →1 |
coalesce(val1,val2...) |
返回第一个非空值 | coalesce(null,1,2) →1 |
case when 条件 then 结果 else 结果 end |
多条件分支 | 统计男女数量 |
经典实战:统计男女数量
-- 方案1:case when 固定值
select
sum(case sex when '男' then 1 else 0 end) 男,
sum(case sex when '女' then 1 else 0 end) 女
from emp_sex;
-- 方案2:if函数(推荐,简洁)
select
sum(if(sex='男',1,0)) 男,
sum(if(sex='女',1,0)) 女
from emp_sex;
六、高级解析函数(JSON/URL)
处理日志、接口数据必备,直接解析非结构化数据。
1. JSON 解析函数
get_json_object(json字符串, '$.字段名'):提取 JSON 指定字段值
select get_json_object('{"name":"jack","age":19}','$.age'); -- 输出19
2. URL 解析函数
parse_url(url, 解析类型, 参数名):解析 URL 协议、域名、路径、参数
-- 1. 获取域名
select parse_url('http://www.baidu.com','HOST'); -- www.baidu.com
-- 2. 获取协议
select parse_url('http://www.baidu.com','PROTOCOL'); -- http
-- 3. 获取指定参数值
select parse_url('http://xxx?k1=v1','QUERY','k1'); -- v1
七、行列转换函数(面试 + 工作高频)
行转列、列转行是 Hive 面试必考题,也是数据聚合核心操作。
1. 行转列(多行→一行)
场景:学生选课表(1 行 1 门课)→ 1 行展示所有选课状态(1 = 选,0 = 未选)
三种实现方案
-- 数据准备
create table courses(id int,course string);
-- 方案1:case when + sum
select id,
sum(case when course='a' then 1 else 0 end) a
from courses group by id;
-- 方案2:if + sum(推荐,简洁)
select id,
sum(if(course='a',1,0)) a
from courses group by id;
-- 方案3:collect_set + array_contains(数组判断)
select id,
if(array_contains(collect_set(course),"a"),1,0) a
from courses group by id;
2. 列转行(一行→多行)
核心函数:explode() + lateral view
-- 炸开Array/Map
select name,hobby from array1 lateral view explode(hobbies) t as hobby;
八、函数速记总结
-
Array 数组:
[下标]取值、size长度、explode炸开、array_contains判断包含、concat_ws数组转字符串; -
Map:
['key']取值、explode行转列、str_to_map字符串转 Map; -
Struct:
.取字段、固定结构数据; -
日期:
current_date当前日期、date_format格式化、datediff算天数; -
字符串:
concat_ws拼接、split切割、explode炸开; -
条件判断:
nvl处理空值、if/case when分支判断; -
高级解析:
get_json_object解析 JSON、parse_url解析 URL; -
行列转换:
explode行转列、sum+if列转行。
总结
这篇 Hive 核心函数手册覆盖了企业开发 95% 的常用场景,新增 Array 数组完整用法,从基础数据类型到高级行列转换,从日期清洗到 JSON 解析,全部附带实战语法 + 案例,无论是新手入门、日常开发,还是面试复习,都能直接使用!
建议保存下来,遇到数据处理问题直接查阅,效率翻倍!如果觉得有用,欢迎点赞 + 收藏 + 转发
更多推荐




所有评论(0)