MySql row_number()序号函数
anlondon Lv6

row_number函数简介

row_number()是一个排名函数,它返回一行的序号,从第一行的1开始。为结果集中的每一行或每组行添加唯一编号。

  • 要求MySQL8.0

不过幸运的是,低版本的MySQL提供了可用于模拟row_number()函数的会话变量。

下面将演示原版和模拟两种方式

MySql 8.0 原生写法

ROW_NUMBER() OVER (<partition_definition> <order_definition>)

常见用法:为行分配序号
以下语句使用ROW_NUMBER()函数为products表中的每一行分配一个序号:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
SELECT 
ROW_NUMBER() OVER (
ORDER BY productName
) row_num,
productName,
msrp
FROM
products
ORDER BY
productName;

# 这是输出
+---------+---------------------------------------------+--------+
| row_num | productName | msrp |
+---------+---------------------------------------------+--------+
| 1 | 18th century schooner | 122.89 |
| 2 | 18th Century Vintage Horse Carriage | 104.72 |
| 3 | 1900s Vintage Bi-Plane | 68.51 |
| 4 | 1900s Vintage Tri-Plane | 72.45 |
| 5 | 1903 Ford Model A | 136.59 |
| 6 | 1904 Buick Runabout | 87.77 |
| 7 | 1911 Ford Town Car | 60.54 |
| 8 | 1912 Ford Model T Delivery Wagon | 88.51 |
| 9 | 1913 Ford Model T Speedster | 101.31 |
| 10 | 1917 Grand Touring Sedan | 170.00 |
| 11 | 1917 Maxwell Touring Car | 99.21 |
| 12 | 1926 Ford Fire Engine | 60.77 |
| 13 | 1928 British Royal Navy Airplane | 109.42 |
...

更多语法见MySQL ROW_NUMBER 函数

模拟 row_number()

** 方法一 **

要模拟row_number()函数,您必须在查询中使用会话变量。

以下语句从employees表中获取5名员工,并从1开始为每行添加行号。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
SET @row_number = 0;
SELECT
( @row_number := @row_number + 1 ) AS num,
firstName,
lastName
FROM
employees
LIMIT 5;

# 这是输出
+------+-----------+-----------+
| num | firstName | lastName |
+------+-----------+-----------+
| 1 | Diane | Murphy |
| 2 | Mary | Phan |
| 3 | Jeff | Firrelli |
| 4 | William | Patterson |
| 5 | Gerard | Bondur |
+------+-----------+-----------+
5 rows in set (0.00 sec)

在上面的陈述中:

  • 在第一个语句中,我们定义了一个名为的变量 row_number,并将其值设置为0.这row_number是由@前缀指示的会话变量。
  • 在第二个语句中,我们从employees表中选择数据,并将每行的 row_number变量值增加到1。LIMIT子句用于约束返回的行数,在这种情况下,它被设置为5。

** 方法二 **
另一种技术是使用会话变量作为派生表,并将其与主表交叉连接。请参阅以下查询:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
SELECT 
(@row_number:=@row_number + 1) AS num, firstName, lastName
FROM
employees,(SELECT @row_number:=0) AS t
LIMIT 5;

# 这是输出
+------+-----------+-----------+
| num | firstName | lastName |
+------+-----------+-----------+
| 1 | Diane | Murphy |
| 2 | Mary | Phan |
| 3 | Jeff | Firrelli |
| 4 | William | Patterson |
| 5 | Gerard | Bondur |
+------+-----------+-----------+
5 rows in set (0.00 sec)

请注意,派生表必须具有自己的别名,以使查询在语法上正确。

更多语法见MySQL 添加序号


参考资料:

 Comments