mysql的row_number()over
时间: 2025-07-04 16:14:23 浏览: 8
MySQL 中的 `ROW_NUMBER() OVER()` 是一个窗口函数,它为查询结果集中的每一行分配一个唯一的连续序号。与 `RANK()` 和 `DENSE_RANK()` 不同,`ROW_NUMBER()` 不会处理重复值,即使排序字段值相同,也会严格按行顺序递增编号[^2]。
### 基本语法
`ROW_NUMBER() OVER()` 函数的基本语法如下:
```sql
ROW_NUMBER() OVER (
[PARTITION BY partition_expression, ... ]
ORDER BY sort_expression [ASC | DESC], ...
)
```
- **PARTITION BY**:可选参数,用于将数据划分为多个分区,每个分区独立计算行号。
- **ORDER BY**:必填参数,指定在每个分区内如何对行进行排序。
### 使用示例
#### 1. 简单使用 `ROW_NUMBER() OVER()`
假设有一个名为 `employees` 的表,包含以下数据:
| id | name | department | salary |
|----|-------|------------|--------|
| 1 | Alice | HR | 5000 |
| 2 | Bob | IT | 6000 |
| 3 | Carol | IT | 5500 |
| 4 | Dave | HR | 4800 |
我们可以使用 `ROW_NUMBER()` 来为每一行分配一个唯一的序号,按照工资从高到低排序:
```sql
SELECT
name,
department,
salary,
ROW_NUMBER() OVER (ORDER BY salary DESC) AS row_num
FROM employees;
```
输出结果如下:
| name | department | salary | row_num |
|-------|------------|--------|---------|
| Bob | IT | 6000 | 1 |
| Carol | IT | 5500 | 2 |
| Alice | HR | 5000 | 3 |
| Dave | HR | 4800 | 4 |
#### 2. 结合 `PARTITION BY` 使用
如果我们希望在每个部门内部单独计算行号,可以使用 `PARTITION BY` 参数。例如,按部门划分,并在每个部门内按工资从高到低分配行号:
```sql
SELECT
name,
department,
salary,
ROW_NUMBER() OVER (PARTITION BY department ORDER BY salary DESC) AS row_num
FROM employees;
```
输出结果如下:
| name | department | salary | row_num |
|-------|------------|--------|---------|
| Alice | HR | 5000 | 1 |
| Dave | HR | 4800 | 2 |
| Bob | IT | 6000 | 1 |
| Carol | IT | 5500 | 2 |
#### 3. 实际应用场景:分组聚合
在某些场景下,`ROW_NUMBER()` 可以与其他聚合函数结合使用。例如,在时间序列数据中,我们可能需要将连续的时间点分成若干组,并对每组进行聚合操作。
以下是一个示例查询,演示了如何将 `ROW_NUMBER()` 与 `FLOOR()` 函数结合使用,将每 4 行数据分为一组,并对每组进行聚合:
```sql
SELECT
MIN(date_time) AS start_datetime,
SUM(value) AS total_value
FROM (
SELECT
date_time,
value,
FLOOR((ROW_NUMBER() OVER (ORDER BY date_time) - 1) / 4) AS group_num
FROM hh_data
WHERE date_time BETWEEN '开始时间' AND '结束时间'
) AS subquery
GROUP BY group_num;
```
在这个查询中,`ROW_NUMBER() OVER (ORDER BY date_time)` 为每一行分配了一个递增的行号,然后通过 `(ROW_NUMBER() - 1) / 4` 将每 4 行数据划分为一个组,最后使用 `GROUP BY` 对每组进行聚合操作[^1]。
---
### 注意事项
- `ROW_NUMBER()` 是非标准 SQL 函数,最早在 MySQL 8.0 版本中引入,因此必须确保数据库版本支持窗口函数。
- 如果需要兼容早期版本(如 MySQL 5.x),可以通过变量模拟 `ROW_NUMBER()` 的功能。
- 在使用 `ROW_NUMBER()` 时,务必提供 `ORDER BY` 子句,否则函数无法确定行号的顺序。
---
###
阅读全文
相关推荐


















