排除 mysql 8.0 中的重复项
Exclude duplicates in mysql 8.0
在升级到 MySQL 8.0 之前,我曾经使用 GROUP BY
来避免 select 重复,但现在我得到:
1055 - Expression #2 of SELECT list is not in GROUP BY clause and contains nonaggregated column 'database.orders.ID' which is not functionally dependent on columns in GROUP BY clause; this is incompatible with sql_mode=only_full_group_by, Time: 0.028000s
我知道我可以按如下方式更改 mysql 模式:
mysql -u root -p
mysql > SET GLOBAL sql_mode=(SELECT REPLACE(@@sql_mode,'ONLY_FULL_GROUP_BY',''));
但我想保留当前模式但解决问题。
此 MySQL 查询有效:
SELECT Country FROM orders GROUP BY Country
+---------+
| Country |
+---------+
| USA |
| UK |
+---------+
但是当我添加另一个 MySQL 列时,例如 ID:
mysql> SELECT Country,ID FROM orders GROUP BY Country;
出现错误,正如有人建议的那样,在我必须将所有 select 列添加到 GROUP BY
之前,查询变为
SELECT Country,ID FROM orders GROUP BY Country, ID
但这并没有删除重复项,而是显示了所有国家/地区。
预期结果是:
mysql> SELECT Country,ID,userID FROM orders GROUP BY Country;
+------+---------+------------+
| ID | Country | UserID |
+------+---------+------------+
| 51 | USA | 99 |
| 61 | UK | 12 |
+------+---------+------------+
注意:列名只是为了简单起见,在我的例子中,每个 "Country" 具有相同的 "UserID"
您需要修改 SELECT 子句,使其使用:
SELECT Country,ANY_VALUE(ID)
上提供了关于为什么会发生这种情况的更详细信息。
为了简化原因,您仅按 A 列分组,但您还想 SELECT B 列值。在分组过程中,MySQL 将折叠所有重复的行,直到保留唯一的 A 列值。但是,对于单个列 A 值,可能有多个不同的列 B 值。 MySQL 不知道它们的优先级,为了将这些多个值折叠成一个标量值,您需要告诉它您想要 select.[= 多个 B 列值中的哪个值。 16=]
MIN()
、MAX()
或 ANY_VALUE()
,如果您确定 B 列的值无论如何都是重复的,并且其中任何一个都可以工作。在 MySQL 的早期版本中,引擎会默认忽略此类差异并应用 ANY_VALUE()
逻辑。
在升级到 MySQL 8.0 之前,我曾经使用 GROUP BY
来避免 select 重复,但现在我得到:
1055 - Expression #2 of SELECT list is not in GROUP BY clause and contains nonaggregated column 'database.orders.ID' which is not functionally dependent on columns in GROUP BY clause; this is incompatible with sql_mode=only_full_group_by, Time: 0.028000s
我知道我可以按如下方式更改 mysql 模式:
mysql -u root -p
mysql > SET GLOBAL sql_mode=(SELECT REPLACE(@@sql_mode,'ONLY_FULL_GROUP_BY',''));
但我想保留当前模式但解决问题。
此 MySQL 查询有效:
SELECT Country FROM orders GROUP BY Country
+---------+
| Country |
+---------+
| USA |
| UK |
+---------+
但是当我添加另一个 MySQL 列时,例如 ID:
mysql> SELECT Country,ID FROM orders GROUP BY Country;
出现错误,正如有人建议的那样,在我必须将所有 select 列添加到 GROUP BY
之前,查询变为
SELECT Country,ID FROM orders GROUP BY Country, ID
但这并没有删除重复项,而是显示了所有国家/地区。
预期结果是:
mysql> SELECT Country,ID,userID FROM orders GROUP BY Country;
+------+---------+------------+
| ID | Country | UserID |
+------+---------+------------+
| 51 | USA | 99 |
| 61 | UK | 12 |
+------+---------+------------+
注意:列名只是为了简单起见,在我的例子中,每个 "Country" 具有相同的 "UserID"
您需要修改 SELECT 子句,使其使用:
SELECT Country,ANY_VALUE(ID)
为了简化原因,您仅按 A 列分组,但您还想 SELECT B 列值。在分组过程中,MySQL 将折叠所有重复的行,直到保留唯一的 A 列值。但是,对于单个列 A 值,可能有多个不同的列 B 值。 MySQL 不知道它们的优先级,为了将这些多个值折叠成一个标量值,您需要告诉它您想要 select.[= 多个 B 列值中的哪个值。 16=]
MIN()
、MAX()
或 ANY_VALUE()
,如果您确定 B 列的值无论如何都是重复的,并且其中任何一个都可以工作。在 MySQL 的早期版本中,引擎会默认忽略此类差异并应用 ANY_VALUE()
逻辑。