rank() over和row_number() over

本文对比了SQL中rank()和row_number()函数的功能差异。rank()用于排序并为相同值分配相同排名,而row_number()则为每一行分配唯一的连续整数。在实现Top N查询时,推荐使用row_number()以确保每条记录都有唯一的标识。

ITPUB上,看到BITI这么说:

 

关于 rank() over 与 row_number() over

刚才在 电子杂志中看见了利用rank实现top n
偶只想提醒一点:

我们通常意义上的top N 的实现应该采用row_number() over 而不是rank
因为row_number 是给记录加一个序号标记
而rank是相当于进行排序后的排名,也就是如果排序列是相同的,那么他们的返回值也是相同的,而row_number则不可能返回相同值

SQL> select * from test;

         A
----------
         1
         2
         1

SQL> select a,rank() over(order by a) from test;

         A RANK()OVER(ORDERBYA)
---------- --------------------
         1                    1
         1                    1
         2                    3

SQL> select a,row_number() over(order by a) from test;

         A ROW_NUMBER()OVER(ORDERBYA)
---------- --------------------------
         1                          1
         1                          2
         2                          3
<think>好的,用户问的是rank_overrow_number的区别。首先,我需要确认这两个函数在SQL中的具体应用区别。 首先,ROW_NUMBER()SQL中的一个窗口函数,它会为每一行分配一个唯一的序号,从1开始递增。不管有没有重复值,每个行都会有一个不同的序号。比如,如果有两个相同的值,它们的ROW_NUMBER()还是会不同,按照顺序排列。 然后是RANK()函数,通常用户可能指的是RANK() OVER()RANK()ROW_NUMBER()的区别在于处理并列排名的方式。当有相同的值时,RANK()会给它们相同的排名,但之后的排名会跳过相应的数字。比如,如果有两个第一名,下一个排名就是第三名,而不是第二名。而ROW_NUMBER()在这种情况下会给出连续的序号,不会有重复。 不过用户提到的“rank_over”可能是一个误解,因为标准SQL中并没有这个函数。可能用户是想说RANK() OVER(),或者某个数据库特有的函数?需要确认这一点。比如,在某些数据库中可能有类似的功能,但通常正确的函数是RANK()DENSE_RANK()。 所以,总结两者的区别: - ROW_NUMBER():为每一行生成唯一且连续的整数,不考虑排序字段的重复值。 - RANK():相同值的行得到相同的排名,但后续排名会跳过,比如1,1,3。 - DENSE_RANK():类似RANK(),但后续排名不跳过,比如1,1,2。 用户可能在使用窗口函数时遇到了问题,或者在编写查询时需要选择适当的排名函数。需要给出具体的例子来说明两者的不同,以及适用的场景。例如,当需要允许并列排名并跳过后续数字时使用RANK(),而需要唯一序号时用ROW_NUMBER()。 另外,用户可能混淆了函数名称,所以需要指出正确的函数名是RANK() OVER(),而不是rank_over。同时,可能还需要提到DENSE_RANK()作为补充,帮助用户全面了解排名函数的不同。 最后,确保回答符合格式要求,包括示例代码相关问题。需要提供SQL的例子,比如对某个表应用这两个函数,显示结果差异。然后生成相关问题,比如如何处理并列排名、DENSE_RANK的作用等。</think>在SQL中,`ROW_NUMBER()` `RANK()`(通常写作 `RANK() OVER()`)是窗口函数,用于生成行号或排名,但它们的逻辑有本质区别。以下是具体差异: ### 1. **ROW_NUMBER()** - **功能**:为每一行分配**唯一且连续**的序号(从1开始递增),不考虑排序字段的重复值。 - **特点**:即使排序字段的值相同,序号也会连续递增。 - **示例**: ```sql SELECT name, score, ROW_NUMBER() OVER (ORDER BY score DESC) AS row_num FROM students; ``` **结果**: ``` | name | score | row_num | |-------|-------|---------| | Alice | 95 | 1 | | Bob | 90 | 2 | | Carol | 90 | 3 | -- 两个90,但序号不同 ``` ### 2. **RANK()** - **功能**:根据排序字段生成排名,**允许并列排名**,但后续排名会跳过。 - **特点**:相同值的行共享相同排名,后续排名跳过重复的数字。 - **示例**: ```sql SELECT name, score, RANK() OVER (ORDER BY score DESC) AS rank_num FROM students; ``` **结果**: ``` | name | score | rank_num | |-------|-------|----------| | Alice | 95 | 1 | | Bob | 90 | 2 | | Carol | 90 | 2 | -- 两个90并列第2名,下一排名跳至4 | Dave | 85 | 4 | ``` ### 3. **DENSE_RANK()**(补充说明) - **功能**:与 `RANK()` 类似,但后续排名**不跳过**。 - **示例**: ```sql SELECT name, score, DENSE_RANK() OVER (ORDER BY score DESC) AS dense_rank_num FROM students; ``` **结果**: ``` | name | score | dense_rank_num | |-------|-------|----------------| | Alice | 95 | 1 | | Bob | 90 | 2 | | Carol | 90 | 2 | -- 两个90并列第2名,下一排名为3 | Dave | 85 | 3 | ``` ### 核心区别总结 | 函数 | 是否允许并列 | 后续排名是否跳过 | 示例输出(相同值) | |---------------|--------------|------------------|--------------------| | `ROW_NUMBER()`| 否 | 无 | 1, 2, 3 | | `RANK()` | 是 | 是 | 1, 2, 2, 4 | | `DENSE_RANK()` | 是 | 否 | 1, 2, 2, 3 | ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值