分组排序
最主要的区别就是如果两个分数相同,排名是否同列以及排名是否相同。

这个方法仅在mysql8.0以后,hive或其他数据库支持

直接看图:原始表

hive 分组top hive 分组排序函数_mysql

原表如上,想要的结果如下

hive 分组top hive 分组排序函数_分页_02

从图中可以发现:

  1. row_number函数:如果并列但名次反而不相同,但是后续的名次是连续的
  2. rank函数:如果并列则名次相同,但是后续的名次会不连续
  3. dense_rank函数:如果并列则名次相同,但是后续的名次是连续的
  4. ntile函数:如果并列则名次相同,后续的名次连续

row_number
基本原理是先使用over子句中的排序语句对记录进行排序,然后再根据这个排序生成序号。

select *, row_number() over (order by score desc) as rank
from score;

查询结果如下

hive 分组top hive 分组排序函数_分页_03

一般在工作中,常用分组排序做web程序的分页,然后我们指定查询范围。
row_number()进阶

rank
作用效果和row_number()方法类似,但是支持并列排名,但排名名次可能不连续。

select *, rank() over (order by score desc) as rank
from score;

查询结果如下

hive 分组top hive 分组排序函数_hive 分组top_04

dense_rank
作用效果和rank()方法类似,不仅支持并列排名,而且排名也是连续的

select *, dense_rank() over (order by score) as rank
from score;

查询结果如下

hive 分组top hive 分组排序函数_hive 分组top_05

ntile
ntile()函数是最好理解,同时也是最不好理解的。结果既能够和其他函数相似,也能够有很大的区别。

select *, ntile(3) over (order by score desc) as rank
from score;

查询结果如下

hive 分组top hive 分组排序函数_hive_06

ntile函数可以对序号进行分组处理,类似于hive的分桶处理:

ntile函数的分桶依据:

1、每组的记录数不能大于它上一组的记录数,即编号小的桶放的记录数不能小于编号大的桶。也就是说,第1组中的记录数只能大于等于第2组及以后各组中的记录数。
2、所有组中的记录数要么都相同,要么从某一个记录较少的组(命名为X)开始后面所有组的记录数都与该组(X组)的记录数相同。也就是说,如果有个组,前三组的记录数都是9,而第四组的记录数是8,那么第五组和第六组的记录数也必须是8。

举个栗子
如果是50条,那么就是
1-10 : 第一组 (十条)
11-20 : 第二组(十条)
21-30 : 第三组(十条)
31-40 : 第四组(十条)
41-50 : 第五组(十条)

如果是51条,那么就是
1-11 : 第一组(十一条)
12-21 : 第二组(十条)
22-31 : 第三组(十条)
32-41 : 第四组(十条)
42-51 : 第五组(十条)

总结
在使用分组排序函数的时候要注意以下三点:

  1. 排名函数必须要有over子句
  2. 排名函数必须要有order by的over子句
  3. 分组内从1开始排序