DENSE_RANK()是一个窗口函数,用来给查询分配排名,且排名值与值之间无间隙。
函数语法
DENSE_RANK() OVER (
PARTITION BY <expression>[{,<expression>...}]
ORDER BY <expression> [ASC|DESC], [{,<expression>...}]
)
PARTITION BY,将FROM字句生成的结果按条件分区,该函数应用于每个分区。ORDER BY,指定每个分区的排序规则。
实例1
准备一个表scores和相应的数据
# 创建表
CREATE TABLE `scores` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`score` decimal(10, 2) NOT NULL,
PRIMARY KEY (`id`)
);
# 数据
INSERT INTO `scores` VALUES (1, 3.50);
INSERT INTO `scores` VALUES (2, 3.65);
INSERT INTO `scores` VALUES (3, 4.00);
INSERT INTO `scores` VALUES (4, 3.85);
INSERT INTO `scores` VALUES (5, 4.00);
INSERT INTO `scores` VALUES (6, 3.65);
查询要求如下
- 分数应按从高到低排列。
- 如果两个分数相等,那么两个分数的排名应该相同。
- 在排名相同的分数后,排名数应该是下一个连续的整数。换句话说,排名之间不应该有空缺的数字。
SQL如下
select score,DENSE_RANK() OVER (
ORDER BY score DESC # 声明按照score降序排序,
) 'rank' # 注意,这里不能直接使用rank,不然会报错,因为rank在MySQL中是一个关键字
from Scores
结果
实例2
准备一个表scores和相应的数据
# 创建表
CREATE TABLE `scores` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`score` decimal(10, 2) NOT NULL,
`classes` int(11) NULL DEFAULT NULL,
PRIMARY KEY (`id`)
);
# 数据
INSERT INTO `scores_plus1` VALUES (1, 3.50, 1);
INSERT INTO `scores_plus1` VALUES (2, 3.65, 1);
INSERT INTO `scores_plus1` VALUES (3, 4.00, 2);
INSERT INTO `scores_plus1` VALUES (4, 3.85, 2);
INSERT INTO `scores_plus1` VALUES (5, 4.00, 2);
INSERT INTO `scores_plus1` VALUES (6, 3.65, 2);
查询要求如上,但是新增一条查询条件
- 分班级排名
SQL如下
select score,classes,DENSE_RANK() OVER (
PARTITION BY classes # 声明按照班级分区
ORDER BY score DESC # 声明分区按照score降序排序,
) 'rank' # 注意,这里不能直接使用rank,不然会报错,因为rank在MySQL中是一个关键字
from Scores
结果