SQL GROUP BY 和 HAVING 子句及示例

什么是 SQL GROUP BY 子句?

GROUP BY 子句是一个 SQL 命令,用于将具有相同值的行分组。GROUP BY 子句用于 SELECT 语句。它还可以选择性地与聚合函数结合使用,以从数据库生成摘要报告。

它就是这样做的,总结数据库中的数据。

包含 GROUP BY 子句的查询称为分组查询,并且每个分组项只返回一行。

SQL GROUP BY 语法

既然我们知道了 SQL GROUP BY 子句是什么,现在让我们看一下基本 group by 查询的语法。

SELECT statements... GROUP BY column_name1[,column_name2,...] [HAVING condition];

HERE

  • “SELECT statements…” 是标准的 SQL SELECT 命令查询。
  • GROUP BY column_name1” 是根据 column_name1 执行分组的子句。
  • “[,column_name2,…]” 是可选的;当在多个列上进行分组时,它代表其他列名。
  • “[HAVING condition]” 是可选的;它用于限制 GROUP BY 子句影响的行。它类似于 WHERE 子句

使用单列分组

为了帮助理解 SQL Group By 子句的效果,让我们执行一个简单的查询,该查询返回 members 表中的所有性别条目。

SELECT `gender` FROM `members` ;
gender
Female
Female
Male
Female
Male
Male
Male
Male
Male

假设我们想获取性别的唯一值。我们可以使用以下查询 –

SELECT `gender` FROM `members` GROUP BY `gender`;

在 MySQL workbench 中针对 Myflixdb 执行上述脚本会得到以下结果。

gender
Female
Male

请注意,只返回了两项结果。这是因为我们只有两种性别类型:男性和女性。SQL 中的 GROUP BY 子句将所有“男性”成员分组在一起,并为其只返回一行。它对“女性”成员也做了同样的处理。

使用多列分组

假设我们想获取电影 category_id 列表以及它们发布的对应年份。

让我们观察这个简单查询的输出

SELECT `category_id`,`year_released` FROM `movies` ;
category_id year_released
1 2011
2 2008
NULL 2008
NULL 2010
8 2007
6 2007
6 2007
8 2005
NULL 2012
7 1920
8 NULL
8 1920

上述结果有许多重复项。

让我们使用 SQL 中的 group by 执行相同的查询 –

SELECT `category_id`,`year_released` FROM `movies` GROUP BY `category_id`,`year_released`;

在 MySQL workbench 中针对 myflixdb 执行上述脚本会得到以下结果,如下所示。

category_id year_released
NULL 2008
NULL 2010
NULL 2012
1 2011
2 2008
6 2007
7 1920
8 1920
8 2005
8 2007

在上面的示例中,GROUP BY 子句同时作用于 category id 和 release year 以标识唯一的行。

如果 category id 相同但 release year 不同,则一行被视为唯一一行。如果 category id 和 release year 对于多行是相同的,则它被视为重复项,并且只显示一行。

分组和聚合函数

假设我们想知道数据库中男性和女性的总数。我们可以使用下面显示的以下脚本来完成。

SELECT `gender`,COUNT(`membership_number`)  FROM `members` GROUP BY `gender`;

在 MySQL Workbench 中针对 myflixdb 执行上述脚本会得到以下结果。

gender COUNT('membership_number')
Female 3
Male 5

下面显示的结果是按每个唯一的性别值分组的,并且使用 COUNT 聚合函数计算分组行的数量。

使用HAVING 子句限制查询结果

我们并不总是想对给定表中的所有数据执行分组。有时我们会想将我们的结果限制在某个特定的标准。在这种情况下,我们可以使用 HAVING 子句。

假设我们想知道电影 category id 为 8 的所有发布年份。我们将使用以下脚本来实现我们的结果。

SELECT * FROM `movies` GROUP BY `category_id`,`year_released` HAVING `category_id` = 8;

在 MySQL workbench 中针对 Myflixdb 执行上述脚本会得到以下结果,如下所示。

movie_id title director year_released category_id
9 Honey mooners John Schultz 2005 8
5 Daddy's Little Girls NULL 2007 8

请注意,只有 category id 为 8 的电影受到了我们 GROUP BY 子句的影响。

摘要

  • SQL 中的 GROUP BY 子句用于按相同值对行进行分组。
  • GROUP BY 子句与 SQL SELECT 语句一起使用。
  • GROUP BY 子句中使用的 SELECT 语句只能包含列名、聚合函数、常量和表达式。
  • SQL HAVING 子句用于限制 GROUP BY 子句返回的结果。
  • MYSQL GROUP BY 子句用于从多个记录收集数据,并通过一个或多个列返回记录集。