MySQL SELECT 语句
最后修改于 2023 年 1 月 10 日
MySQL 教程的这一部分将详细介绍 MySQL 理解的 SELECT 语句。
检索数据
以下 SQL 语句是最常见的语句之一。它也是最昂贵的语句之一。
mysql> SELECT * FROM Cars; +----+------------+--------+ | Id | Name | Cost | +----+------------+--------+ | 1 | Audi | 52642 | | 2 | Mercedes | 57127 | | 3 | Skoda | 9000 | | 4 | Volvo | 29000 | | 5 | Bentley | 350000 | | 6 | Citroen | 21000 | | 7 | Hummer | 41400 | | 8 | Volkswagen | 21600 | +----+------------+--------+ 8 rows in set (0.00 sec)
这里我们从 Cars 表中检索所有数据。
选择特定列
我们可以使用 SELECT 语句来检索特定列。列名紧随 SELECT 关键字之后。
mysql> SELECT Name, Cost FROM Cars; +------------+--------+ | Name | Cost | +------------+--------+ | Audi | 52642 | | Mercedes | 57127 | | Skoda | 9000 | | Volvo | 29000 | | Bentley | 350000 | | Citroen | 21000 | | Hummer | 41400 | | Volkswagen | 21600 | +------------+--------+ 8 rows in set (0.00 sec)
我们检索 Name 和 Cost 列。列名之间用逗号分隔。
重命名列名
我们可以重命名返回结果集的列名。为此,我们使用 AS 子句。
mysql> SELECT Name, Cost AS Price FROM Cars; +------------+--------+ | Name | Price | +------------+--------+ | Audi | 52642 | | Mercedes | 57127 | | Skoda | 9000 | | Volvo | 29000 | | Bentley | 350000 | | Citroen | 21000 | | Hummer | 41400 | | Volkswagen | 21600 | +------------+--------+ 8 rows in set (0.00 sec)
假设我们想将列名命名为 price 而不是 cost。使用上面的 SQL 语句,我们已经完成了这个操作。
限制数据输出
正如我们上面提到的,当处理大量数据时,检索所有数据是昂贵的。我们可以使用 LIMIT 子句来限制语句返回的数据量。
mysql> SELECT * FROM Cars LIMIT 4; +----+----------+-------+ | Id | Name | Cost | +----+----------+-------+ | 1 | Audi | 52642 | | 2 | Mercedes | 57127 | | 3 | Skoda | 9000 | | 4 | Volvo | 29000 | +----+----------+-------+ 4 rows in set (0.00 sec)
LIMIT 子句将返回的行数限制为 4。
使用两个参数,LIMIT 从偏移量开始返回行。
mysql> SELECT * FROM Cars LIMIT 2, 4; +----+---------+--------+ | Id | Name | Cost | +----+---------+--------+ | 3 | Skoda | 9000 | | 4 | Volvo | 29000 | | 5 | Bentley | 350000 | | 6 | Citroen | 21000 | +----+---------+--------+ 4 rows in set (0.00 sec)
第一个值是偏移量,第二个是返回的行数。这里我们选择最多四行的数据,我们从第三行开始。
mysql> SELECT * FROM Cars LIMIT 4 OFFSET 2; +----+---------+--------+ | Id | Name | Cost | +----+---------+--------+ | 3 | Skoda | 9000 | | 4 | Volvo | 29000 | | 5 | Bentley | 350000 | | 6 | Citroen | 21000 | +----+---------+--------+ 4 rows in set (0.00 sec)
为了与 PostgreSQL 数据库兼容,MySQL 也有 OFFSET 关键字。上面的代码与之前的例子等效。
排序数据
我们使用 ORDER BY 子句对返回的数据集进行排序。ORDER BY 子句之后是进行排序的列。ASC 关键字按升序排序数据,DESC 按降序排序。
mysql> SELECT Name, Cost FROM Cars ORDER BY Cost DESC; +------------+--------+ | Name | Cost | +------------+--------+ | Bentley | 350000 | | Mercedes | 57127 | | Audi | 52642 | | Hummer | 41400 | | Volvo | 29000 | | Volkswagen | 21600 | | Citroen | 21000 | | Skoda | 9000 | +------------+--------+ 8 rows in set (0.00 sec)
在上面的 SQL 语句中,我们从 Cars 表中选择 name, cost 列,并按汽车的成本降序排序。所以最贵的车排在最前面。
使用 WHERE 子句选择特定行
在下面的例子中,我们将使用 Orders 表。
mysql> SELECT * FROM Orders; +----+------------+------------+ | Id | OrderPrice | Customer | +----+------------+------------+ | 1 | 1200 | Williamson | | 2 | 200 | Robertson | | 3 | 40 | Robertson | | 4 | 1640 | Smith | | 5 | 100 | Robertson | | 6 | 50 | Williamson | | 7 | 150 | Smith | | 8 | 250 | Smith | | 9 | 840 | Brown | | 10 | 440 | Black | | 11 | 20 | Brown | +----+------------+------------+ 11 rows in set (0.00 sec)
这里我们看到 Orders 表中的所有数据。
接下来,我们要选择一个特定的行。
mysql> SELECT * FROM Orders WHERE Id=6; +----+------------+------------+ | Id | OrderPrice | Customer | +----+------------+------------+ | 6 | 50 | Williamson | +----+------------+------------+ 1 row in set (0.00 sec)
上面的 SQL 语句选择 Id 为 6 的行。
mysql> SELECT * FROM Orders WHERE Customer="Smith"; +----+------------+----------+ | Id | OrderPrice | Customer | +----+------------+----------+ | 4 | 1640 | Smith | | 7 | 150 | Smith | | 8 | 250 | Smith | +----+------------+----------+ 3 rows in set (0.00 sec)
上面的 SQL 语句选择由 Smith 客户创建的所有订单。
我们可以使用 LIKE 关键字在数据中查找特定的模式。
mysql> SELECT * FROM Orders WHERE Customer LIKE "B%"; +----+------------+----------+ | Id | OrderPrice | Customer | +----+------------+----------+ | 9 | 840 | Brown | | 10 | 440 | Black | | 11 | 20 | Brown | +----+------------+----------+ 3 rows in set (0.00 sec)
此 SQL 语句选择所有客户名称以 B 字符开头的订单。
删除重复项
DISTINCT 关键字用于仅从结果集中选择唯一项。
mysql> SELECT Customer FROM Orders WHERE Customer LIKE 'B%'; +----------+ | Customer | +----------+ | Brown | | Black | | Brown | +----------+ 3 rows in set (0.00 sec)
这次我们选择了名称以 B 字符开头的客户。我们可以看到 Brown 被提到了两次。要删除重复项,我们使用 DISTINCT 关键字。
mysql> SELECT DISTINCT Customer FROM Orders WHERE Customer LIKE 'B%'; +----------+ | Customer | +----------+ | Brown | | Black | +----------+ 2 rows in set (0.00 sec)
这是正确的解决方案。
假设我们想知道 Brown 客户下了多少个订单。我们将使用 COUNT() 函数。
mysql> SELECT COUNT(Customer) AS "Orders by Brown" FROM Orders WHERE Customer="Brown"; +-----------------+ | Orders by Brown | +-----------------+ | 2 | +-----------------+ 1 row in set (0.00 sec)
该客户下了两个订单。
分组数据
GROUP BY 子句用于将具有相同值的数据库记录合并为一条记录。它经常与聚合函数一起使用。
假设我们想找出每个客户的订单总和。
mysql> SELECT SUM(OrderPrice) AS Total, Customer FROM Orders GROUP BY Customer; +-------+------------+ | Total | Customer | +-------+------------+ | 440 | Black | | 860 | Brown | | 340 | Robertson | | 2040 | Smith | | 1250 | Williamson | +-------+------------+ 5 rows in set (0.00 sec)
SUM() 关键字返回数值列的总和。GROUP BY 子句将总和分配给客户。因此我们可以看到 Black 订购了 440 个物品或 Smith 订购了 2040 个物品。
当使用聚合函数时,我们不能使用 WHERE 子句。我们使用 HAVING 子句代替。
mysql> SELECT SUM(OrderPrice) AS Total, Customer FROM Orders
-> GROUP BY Customer HAVING SUM(OrderPrice)>1000;
+-------+------------+
| Total | Customer |
+-------+------------+
| 2040 | Smith |
| 1250 | Williamson |
+-------+------------+
2 rows in set (0.00 sec)
上面的 SQL 语句选择总订单超过 1000 单元的客户。
将数据选择到文件中
SELECT 语句可用于将数据从表写入文件。
mysql> SELECT * INTO OUTFILE '/tmp/cars.txt'
-> FIELDS TERMINATED BY ','
-> LINES TERMINATED BY '\n'
-> FROM Cars;
Query OK, 8 rows affected (0.00 sec)
我们将数据从 Cars 表写入 cars.txt 文件。输出文件是 CSV(逗号分隔值)文件。请注意,此操作容易出错,我们很容易遇到权限被拒绝的错误。
$ cat /tmp/cars.txt 1,Audi,52642 2,Mercedes,57127 3,Skoda,9000 4,Volvo,29000 5,Bentley,350000 6,Citroen,21000 7,Hummer,41400 8,Volkswagen,21600
我们可以做相反的操作;将数据从文件加载到表中。
mysql> DELETE FROM Cars; Query OK, 8 rows affected (0.00 sec) mysql> SELECT * FROM Cars; Empty set (0.00 sec)
我们从 Cars 表中删除所有行。
mysql> LOAD DATA INFILE '/tmp/cars.txt'
-> INTO TABLE Cars
-> FIELDS TERMINATED BY ','
-> LINES TERMINATED BY '\n';
Query OK, 8 rows affected (0.00 sec)
Records: 8 Deleted: 0 Skipped: 0 Warnings: 0
mysql> SELECT * FROM Cars;
+----+------------+--------+
| Id | Name | Cost |
+----+------------+--------+
| 1 | Audi | 52642 |
| 2 | Mercedes | 57127 |
| 3 | Skoda | 9000 |
| 4 | Volvo | 29000 |
| 5 | Bentley | 350000 |
| 6 | Citroen | 21000 |
| 7 | Hummer | 41400 |
| 8 | Volkswagen | 21600 |
+----+------------+--------+
8 rows in set (0.00 sec)
我们使用 LOAD DATA INFILE 语句将数据加载回表中。我们验证数据是否已正确加载。
在 MySQL 教程的这一部分中,我们更详细地提到了 SQL SELECT 语句。