one*_*All 5 mysql oracle aggregate group-by distinct
我看到以下同时使用 DISTINCT 和 GROUP BY 的 MySQL 查询:
SELECT DISTINCT user_id, post_id, post_content
FROM some_table
GROUP BY post_id, user_id
HAVING post_content LIKE '%abc%';
Run Code Online (Sandbox Code Playgroud)
这是一个与查询一起使用的场景:每个用户都有一个唯一的 id,user_id
,并且可以发表多个由唯一 id 标识的帖子post_id
。每个帖子都会包含一些文本。
我发现这令人困惑(来自 Oracle DB 之后)并有以下问题:
GROUP BY
而不做任何聚合是什么意思?SELECT
vs in中切换列的顺序有什么意义GROUP BY
?GROUP BY
?DISTINCT
与 一起使用GROUP BY
?在对最终结果或之前完成所有分组之后,是否运行不同的操作?在旧版本的 MySQL 中允许部分分组的疯狂能力必须成为最引起 IT 行业混乱的最有力竞争者之一。
给定表格:
CREATE TABLE t
( x int not null primary key
, y int not null
);
INSERT INTO t (x,y) VALUES (1,1),(1,2);
Run Code Online (Sandbox Code Playgroud)
该声明
SELECT x, y FROM t GROUP BY x
Run Code Online (Sandbox Code Playgroud)
可能意味着 (1,1) 或 (1,2),MySQL 将随机返回其中之一。在这种情况下,DISTINCT 并不重要,结果仍然是不确定的。
SQL92 要求 select 子句中的所有列(聚合列和常量除外)都是 GROUP BY 子句的一部分。
SQL99 稍微放松了这个限制,并允许我们从 GROUP BY 中删除在功能上依赖于其余列的列。IE
CREATE TABLE t
( x int not null primary key
, y int not null
);
SELECT x, y FROM t GROUP by x
Run Code Online (Sandbox Code Playgroud)
有效,因为 y 是 x 的 fd
令人惊讶的是(对我来说)MySQL 的更高版本在实现 SQL99 版本方面是同类中最好的。我最近没有检查过,但是当我检查时,MySQL 很好地处理了相当复杂的场景,而 PostgreSQL 只处理了琐碎的场景。
回答您的问题
1)
SELECT x, y FROM t GROUP BY x, y
Run Code Online (Sandbox Code Playgroud)
表示x,y的组合是一个群。在所有可能的情况下,我认为这与:
SELECT DISTINCT x, y FROM t
Run Code Online (Sandbox Code Playgroud)
由于它们在不同时间进行逻辑评估,因此可能存在一些实际不同的极端情况(但我想不出一个)
2)无,在这方面它们是一组列,因此没有顺序
3) 见上文。
4) SQL 查询计算的逻辑顺序是:
FROM, JOIN
WHERE
GROUP BY
HAVING
SELECT
DISTINCT
ORDER BY
FETCH FIRST
Run Code Online (Sandbox Code Playgroud)
因此 GROUP BY 应该在 DISTINCT 之前进行评估。我想不出在什么情况下这会很重要。
在您的查询中,我怀疑有人得到了令人困惑的结果,并尝试使用 DISTINCT 获得另一个结果。他们可能很幸运(或不幸)得到了他们期望的结果,所以 DISTINCT 留下来了。但错误仍然存在
ad 1)旧的mysql数据库,当您禁用ONLY_FULL_GROUP_BY时,您可以进行此查询,如果 post_content 全部相等,您会注意到,mysql 会返回一个随机的不确定值。
ad 2) 从来没有
ad 3) 惰性编程,当您启用ONLY_FULL_GROUP_BY时会发生错误
ad 4) 否,它会显示连接到 user_id 的所有 post_content,post_id 类似于 addind post_content to the Group by
就像草莓已经说过这个查询没有任何意义