hive窗口分析函數使用詳解系列一

1.綜述

Hive的聚合函數衍生的窗口函數在我們進行數據處理和數據分析過程中起到了很大的作用

在Hive中,窗口函數允許你在結果集的行上進行計算,這些計算不會影響你查詢的結果集的行數。

Hive提供的窗口和分析函數可以分爲聚合函數類窗口函數,分組排序類窗口函數,偏移量計算類窗口函數。

本節主要介紹聚合函數類窗口函數的常見使用場景。

1.1.常見聚合類開窗函數

count() over();
sum() over();
max() over();
min() over();
avg() over();

1.2.分析函數語法

分析函數 over(partition by 列名 order by 列名 rows between 開始位置 and 結束位置)

具體解析

over()括號內爲空時,是直接進行聚合計算。

其中partition by 列名 是按指定列進行分組,進而進行聚合計算。

最後的order by 列名 是按照指定列進行排序,進而進行聚合計算。

1.3.基礎數據準備

create table if not exists temp.user_info (
  `id` bigint comment '用戶id',
  `client` string comment '客戶端',
  `gender` int comment '性別,0女1男',
  `constellation` string comment '星座',
  `age` int comment '年齡',
  `pv` bigint comment '訪問量',
  `chat_num` bigint comment '聊天次數'
) comment '用戶信息測試臨時表' 

數據預覽

id client gender constellation age pv chat_num
1 ios 0 處女座 29 174 3
2 ios 1 雙魚座 26 263 2
3 android 1 雙魚座 35 232 39
4 ios 1 水瓶座 32 57 3
5 ios 1 射手座 33 67 6
6 ios 1 雙子座 36 81 5
7 ios 1 獅子座 29 68 4
8 ios 1 獅子座 28 19 3
9 ios 0 射手座 32 479 2
10 ios 1 白羊座 26 255 36

2.over窗口爲空時的計算

over()括號內爲空的計算比較簡單,主要應用場景爲保留數據明細的同時,增加額外的列進行數據聚合計算

1.1.sum求解總訪問量總和及用戶明細列表。

-- over()括號內爲空時,是直接進行聚合計算
select id,client,gender,age,pv,sum(pv) over() as total_pv from temp.user_info where  id <= 10
order by id

數據結果

id client gender age pv total_pv
1 ios 0 29 174 1695
2 ios 1 26 263 1695
3 android 1 35 232 1695
4 ios 1 32 57 1695
5 ios 1 33 67 1695
6 ios 1 36 81 1695
7 ios 1 29 68 1695
8 ios 1 28 19 1695
9 ios 0 32 479 1695
10 ios 1 26 255 1695

可以看到給出了數據明細,並且在每行明細後增加了累積求和值。

1.2.count查詢用戶總量及用戶明細列表。

select id,client,gender,age,pv,count(id) over() as total_count from temp.user_info where  id <= 10
order by id

數據結果

id client gender age pv total_count
1 ios 0 29 174 10
2 ios 1 26 263 10
3 android 1 35 232 10
4 ios 1 32 57 10
5 ios 1 33 67 10
6 ios 1 36 81 10
7 ios 1 29 68 10
8 ios 1 28 19 10
9 ios 0 32 479 10
10 ios 1 26 255 10

給出了數據明細,並且在明細後增加了當前總用戶數。

1.3.max查詢用戶最大訪問量及用戶明細

-- max()查詢用戶最大訪問量及用戶明細
select id,client,gender,age,pv,max(pv) over() as max_pv from temp.user_info where  id <= 10
order by id

數據結果

id client gender age pv max_pv
1 ios 0 29 174 479
2 ios 1 26 263 479
3 android 1 35 232 479
4 ios 1 32 57 479
5 ios 1 33 67 479
6 ios 1 36 81 479
7 ios 1 29 68 479
8 ios 1 28 19 479
9 ios 0 32 479 479
10 ios 1 26 255 479

給出了數據明細,並在最後列增加了用戶最大訪問量數據

min() 同理

1.4.avg查詢用戶平均訪問量及用戶明細

select id,client,gender,age,pv,avg(pv) over() as avg_pv from temp.user_info where  id <= 10
order by id

數據結果

id client gender age pv avg_pv
1 ios 0 29 174 169.5
2 ios 1 26 263 169.5
3 android 1 35 232 169.5
4 ios 1 32 57 169.5
5 ios 1 33 67 169.5
6 ios 1 36 81 169.5
7 ios 1 29 68 169.5
8 ios 1 28 19 169.5
9 ios 0 32 479 169.5
10 ios 1 26 255 169.5

給出了數據明細,並在最後列增加了用戶平均訪問量。

2.指定列進行分組的聚合計算

2.1.sum求解不同年齡段總訪問量總和及用戶明細

select *,sum(pv) over(partition by age) as total_pv from temp.user_info where  id <= 10
order by age

數據結果

id client gender age pv avg_pv
2 ios 1 26 263 518
10 ios 1 26 255 518
8 ios 1 28 19 19
1 ios 0 29 174 242
7 ios 1 29 68 242
4 ios 1 32 57 536
9 ios 0 32 479 536
5 ios 1 33 67 67
3 android 1 35 232 232
6 ios 1 36 81 81

可以看到最後的total_pv 是按照年齡段分組進行累加的

2.2.count求解不同客戶端總用戶數及用戶明細列表

select id,client,gender,age,pv,count(id) over(partition by client) as count_total from temp.user_info where  id <= 10
order by id

數據結果

id client gender age pv count_total
1 ios 0 29 174 9
2 ios 1 26 263 9
3 android 1 35 232 1
4 ios 1 32 57 9
5 ios 1 33 67 9
6 ios 1 36 81 9
7 ios 1 29 68 9
8 ios 1 28 19 9
9 ios 0 32 479 9
10 ios 1 26 255 9

可以看到最後count_total 是按client分組進行計數的

2.3.max求解不同年齡段最大訪問量及用戶明細列表

select id,client,gender,age,pv,max(pv) over(partition by age) as count_total from temp.user_info where  id <= 10
order by age

數據結果

id client gender age pv count_total
10 ios 1 26 255 263
2 ios 1 26 263 263
8 ios 1 28 19 19
7 ios 1 29 68 174
1 ios 0 29 174 174
4 ios 1 32 57 479
9 ios 0 32 479 479
5 ios 1 33 67 67
3 android 1 35 232 232
6 ios 1 36 81 81

可以看到進行了分組求最大值。

min以及avg同理,不再舉例。

3.指定列進行分組和排序的聚合計算

3.1.sum按性別分組截止當前年齡總訪問量及用戶明細列表

select id,client,gender,age,pv,sum(pv) over(partition by gender order by age) as total_pv from temp.user_info where  id <= 10
order by gender

數據結果

id client gender age pv total_pv
1 ios 0 29 174 174
9 ios 0 32 479 653
2 ios 1 26 263 518
10 ios 1 26 255 518
8 ios 1 28 19 537
7 ios 1 29 68 605
4 ios 1 32 57 662
5 ios 1 33 67 729
3 android 1 35 232 961
6 ios 1 36 81 1042

數據解釋:可以看到上述數據,性別爲女的29歲及之前年齡段訪問pv爲174次,女性32歲及之前年齡訪問總和pv爲653次。

同理男性,不同年齡段及之前年齡的累加數據如上表,且相同年齡的累加值是一致的。

3.2.按性別分組截止當前年齡最大用戶訪問量及用戶明細列表

select id,client,gender,age,pv,max(pv) over(partition by gender order by age) as max_pv from temp.user_info where  id <= 10
order by gender

數據明細

id client gender age pv max_pv
1 ios 0 29 174 174
9 ios 0 32 479 479
2 ios 1 26 263 263
10 ios 1 26 255 263
8 ios 1 28 19 263
7 ios 1 29 68 263
4 ios 1 32 57 263
5 ios 1 33 67 263
3 android 1 35 232 263
6 ios 1 36 81 263

可以看到男性最大訪問量爲263

min以及avg同理,不再舉例。

3.3.按性別分組截止當前年齡用戶總數

select id,client,gender,age,pv,count(id) over(partition by gender order by age) as count_uv from temp.user_info where  id <= 10
order by gender,age

數據結果

id client gender age pv count_uv
1 ios 0 29 174 1
9 ios 0 32 479 2
2 ios 1 26 263 2
10 ios 1 26 255 2
8 ios 1 28 19 3
7 ios 1 29 68 4
4 ios 1 32 57 5
5 ios 1 33 67 6
3 android 1 35 232 7
6 ios 1 36 81 8

分組累加求和

綜合以上內容,第一部分和第二部分可以通過聚合函數+join的形式實現,但第三部分排序累加計數,實現起來比較困難,而這部分在一些需要分組累加彙總的場景使用很方便。

下一期:hive窗口分析函數使用攻略之二-分組排序窗口函數

按例,歡迎點擊此處關注我的個人公衆號,交流更多知識。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章