row_number over()的使用:

假如我们有这样一组数据,我们需要求出不同性别的年龄top2的人的信息。这个时候怎么做?

可能我们会首先想到分组,但是分组只能值top1,怎么样能求出top2,top3呢?这时候我们想如果分组后能够按照年龄排序然后标出来序号就好了!

id   age  name sex

1,18,xiaoli,male
2,19,wang,male
3,22,liu,female
4,16,dawei,male
5,30,erbao,male
6,26,xiao,female
7,18,chengua,male


下面就介绍一个非常有用的函数:row_number() over()他的作用就是分组排序加上序号标记

比如以上求解不同性别的年龄top2,我们可以这样做:

建表导入数据:

create table rownumber(id string,age int,name string,sex string)
row format delimited
fields terminated by ',';
load data local inpath '/root/mytest/rowover.dat' into table rownumber;


Hive窗口函数 row_number over()和sum() over()的使用详解_HIVE

select id,age,name,sex,
row_number() over(partition by sex order by age desc) as rownumber
from rownumber;


Hive窗口函数 row_number over()和sum() over()的使用详解_HIVE_02

我们可以清楚的看到 row_number() over(partition by sex order by age desc) as rownumber

就相当于增加了一列序号,over()中partition by sex是按照sex分组,order by age desc按照年龄降序排序,然后row_number()在加上序号。

select id,age,name,sex
from
(select id,age,name,sex,
row_number() over(partition by sex order by age desc) as rownumber
from rownumber ) temp
where rownumber<3;


Hive窗口函数 row_number over()和sum() over()的使用详解_HIVE_03

这样就求出分组topn了,很方便!

sum() over()的使用:

有这样的数据:第一列name,第二列月份mon,第三列金额jine

A,2015-01,5

A,2015-01,15

B,2015-01,5

A,2015-01,8

B,2015-01,25

A,2015-01,5

C,2015-01,10

C,2015-01,20

A,2015-02,4

A,2015-02,6

C,2015-02,30

C,2015-02,10

B,2015-02,10

B,2015-02,5

A,2015-03,14

A,2015-03,6

B,2015-03,20

B,2015-03,25

C,2015-03,10

C,2015-03,20

我们需要求出对于每个人的一个月的总额和累计到当前月的总额。

传统方法非常的麻烦,具体思路是;先求出月总额表(name,mon,amount),然后讲月总额表自联结,在过滤当前月份后面的月份,最终在求和。

使用sum() over()可以轻松给解决,sum()首先我们都知道是求和,加上over()就是针对某个窗口求和了,具体哪个窗口呢?

具体实现:

求出每月的总额 放到表中,先将数据加载到表中,在求月总额

create table monsum(name string,mon string,jine string)
row format delimited
fields terminated by ',';
load data local inpath '/root/mytest/sumreport.dat' into table monsum;

--求出月总额
create table monamount
as
select name,mon,sum(jine) as amount
from monsum
group by name,mon;


Hive窗口函数 row_number over()和sum() over()的使用详解_数据加载_04

然后使用窗口函数求出累计当前月总额,

select name,mon,amount,
sum(amount) over(partition by name order by mon rows between unbounded preceding and current row) as account
from monamount;


Hive窗口函数 row_number over()和sum() over()的使用详解_HIVE_05

sum(amount)的求和是针对后面over()窗口的求和,

over中partition by name order by mon 针对name这一组按照月份排序,rows between unbounded preceding and current 限定了行是按照在当前行不限定的往前处理,通俗就是处理当前以及之前的所有行的sum,即3月时sum(amount)求的时123月的和,2月时sum(amount)求的是12月的和。unbounded意思无限的 preceding在之前的,current row当前行。