SQL ORDER BY 子句

在本教程中,你将学习如何对 SQL 中的 SELECT 查询返回的数据进行排序。

对结果排序

通常,当你使用 SELECT 语句从表中获取数据时,结果集中的行不按任何特定顺序排列。如果希望以特定顺序设置结果集,则可以在语句末尾指定 ORDER BY 子句,该子句告诉服务器如何对查询返回的数据进行排序。默认排序顺序为升序。

语法

ORDER BY 子句用于按查询升序或降序对查询返回的数据进行排序。该子句的基本语法如下:

SELECT column_list FROM table_name ORDER BY column_name ASC | DESC ; 

这里,column_list 是要获取其值的数据库表的列/字段的*名称*,如*名称*, *年龄*, 国家 / *地区*等,而 column_name 是要排序的列的名称。让我们看一些示例来说明它是如何工作的。

考虑我们的数据库中有一个 employees 表,其中包含以下记录:

+--------+--------------+------------+--------+---------+
| emp_id | emp_name     | hire_date  | salary | dept_id |
+--------+--------------+------------+--------+---------+
|      1 | Ethan Hunt   | 2001-05-01 |   5000 |       4 |
|      2 | Tony Montana | 2002-07-15 |   6500 |       1 |
|      3 | Sarah Connor | 2005-10-18 |   8000 |       5 |
|      4 | Rick Deckard | 2007-01-03 |   7200 |       3 |
|      5 | Martin Blank | 2008-06-24 |   5600 |    NULL |
+--------+--------------+------------+--------+---------+

排序单列

以下 SQL 语句将返回 employees 表中的所有员工,并按 emp_name 列按升序对结果集进行排序。

SELECT * FROM employees 
ORDER BY emp_name ASC;

你可以省略 ASC 选项并只使用以下语法。它返回与前一个语句相同的结果集,因为默认排序顺序是升序:

SELECT * FROM employees 
ORDER BY emp_name;

执行上面的命令后,你会得到这样的输出:

+--------+--------------+------------+--------+---------+
| emp_id | emp_name     | hire_date  | salary | dept_id |
+--------+--------------+------------+--------+---------+
|      1 | Ethan Hunt   | 2001-05-01 |   5000 |       4 |
|      5 | Martin Blank | 2008-06-24 |   5600 |    NULL |
|      4 | Rick Deckard | 2007-01-03 |   7200 |       3 |
|      3 | Sarah Connor | 2005-10-18 |   8000 |       5 |
|      2 | Tony Montana | 2002-07-15 |   6500 |       1 |
+--------+--------------+------------+--------+---------+

同样,你可以使用 DESC 选项按降序执行排序。以下语句将按降序排列数字 salary 列的结果集。

SELECT * FROM employees 
ORDER BY salary DESC;

这一次,你将获得如下结果集:

+--------+--------------+------------+--------+---------+
| emp_id | emp_name     | hire_date  | salary | dept_id |
+--------+--------------+------------+--------+---------+
|      3 | Sarah Connor | 2005-10-18 |   8000 |       5 |
|      4 | Rick Deckard | 2007-01-03 |   7200 |       3 |
|      2 | Tony Montana | 2002-07-15 |   6500 |       1 |
|      5 | Martin Blank | 2008-06-24 |   5600 |    NULL |
|      1 | Ethan Hunt   | 2001-05-01 |   5000 |       4 |
+--------+--------------+------------+--------+---------+

排序多列

你还可以在排序时指定多个列。但是,在表中存在重复值之前,结果集中的更改将不可见。好吧,让我们来看看:

为了更好地理解多列排序,我们假设我们在数据库中有一个名为 trainees 的表,其中包含以下记录:

+----+------------+------------+-------------+--------+
| id | first_name | last_name  | birth_date  | gender |
+----+------------+------------+-------------+--------+
|  1 | Peter      | Parker     | 1998-03-04  |  M     |
|  2 | Harry      | Potter     | 2001-08-30  |  M     |
|  3 | Peter      | Pan        | 2004-09-19  |  M     |
|  4 | Alice      | Kingsleigh | 1999-07-02  |  F     |
|  5 | John       | Connor     | 2002-01-15  |  M     |
+----+------------+------------+-------------+--------+

如果你仔细看表,你会发现我们有一些重复的值。然而,受训者 Peter ParkerPeter Pan 的全名不同,但他们的名是相同的。

现在执行以下命令,该命令对 first_name 列的结果集进行*排序*。

SELECT * FROM trainees 
ORDER BY first_name;

执行后,你将获得如下输出:

+----+------------+------------+-------------+--------+
| id | first_name | last_name  | birth_date  | gender |
+----+------------+------------+-------------+--------+
|  4 | Alice      | Kingsleigh | 1999-07-02  |  F     |
|  2 | Harry      | Potter     | 2001-08-30  |  M     |
|  5 | John       | Connor     | 2002-01-15  |  M     |
|  1 | Peter      | Parker     | 1998-03-04  |  M     |
|  3 | Peter      | Pan        | 2004-09-19  |  M     |
+----+------------+------------+-------------+--------+

现在执行此语句,该语句按 first_namelast_name 列对结果集进行*排序*。

SELECT * FROM trainees 
ORDER BY first_name, last_name;
+----+------------+------------+-------------+--------+
| id | first_name | last_name  | birth_date  | gender |
+----+------------+------------+-------------+--------+
|  4 | Alice      | Kingsleigh | 1999-07-02  |  F     |
|  2 | Harry      | Potter     | 2001-08-30  |  M     |
|  5 | John       | Connor     | 2002-01-15  |  M     |
|  3 | Peter      | Pan        | 2004-09-19  |  M     |
|  1 | Peter      | Parker     | 1998-03-04  |  M     |
+----+------------+------------+-------------+--------+

你是否注意到之前和当前结果集之间的差异 - 这次受训者 Peter Parker 的记录是在 Peter Pan 之后。

由于两名受训者的名字相同,即 Peter,因此在这两名学员的 last_name 栏中进行第二级排序,这就是为什么受训者 Peter Parker 的记录在 Peter Pan 之后出现的原因。

注意: 如果指定了多个排序列,则结果集最初按第一列排序,然后该排序列表按第二列排序,依此类推。