SELECT DISTINCT a.s_id, select2Result.s_id, select2Result."mNrPhone",
select2Result."dNrPhone"
FROM "Table1" AS a INNER JOIN
(
SELECT b.s_id, c."mNrPhone", c."dNrPhone" FROM "Table2" AS b, "Table3" AS c
WHERE b.a_id = 1001 AND b.s_id = c.s_id
ORDER BY b.last_name) AS select2Result
ON a.a_id = select2Result.student_id
WHERE a.k_id = 11211
它返回:
1001;1001;"";""
1002;1002;"";""
1002;1002;"2342342232123";"2342342"
1003;1003;"";""
1004;1004;"";""
1002值重复两次,但不应该因为我使用DISTINCT
并且其他表没有重复两次的ID。
答案 0 :(得分:2)
限定符DISTINCT适用于整行,而不适用于选择列表中的第一列。由于第3列和第4列(mNrPhone
和dNrPhone
)对于s_id = 1002
的两行不同,因此DBMS会正确列出这两行。如果您只希望s_id = 1002
出现一次,则必须以不同方式编写查询,并且必须决定要显示哪些辅助数据。
另外,强烈建议您始终在所有查询和子查询中使用显式JOIN表示法(在SQL-92中引入)。不要使用旧的隐式连接表示法(这是SQL-86或SQL-89中提供的所有表示法),尤其是不要混合使用显式和隐式连接符号(其中子查询使用隐式连接,但是主查询使用显式连接)。您需要知道旧的表示法,以便了解旧的查询。您应该用新表示法编写新查询。
答案 1 :(得分:2)
您可以像这样使用DISTINCT ON:
SELECT DISTINCT ON (a.s_id)
a.s_id, select2Result.s_id, select2Result."mNrPhone",
select2Result."dNrPhone"
...
但正如其他人告诉你的那样,“重复记录”确实不同。
答案 2 :(得分:1)
首先,显示的查询根本不起作用,子查询中 student_id
缺失。你稍后在JOIN中使用它。
更有趣的是:
DISTINCT
DISTINCT
和DISTINCT ON
通过根据要显示的列集对所有行进行排序来返回不同的值,然后从每个集合中选取第一行。它按一般DISTINCT
的所有行排序,仅对DISTINCT ON
的指定行排序。这里有机会从一组中挑选出某些行。
例如,如果您希望在示例中使用非空“mNrPhone”的行:
SELECT DISTINCT ON (a.s_id) -- sure you didn't want a.a_id?
,a.s_id AS a_s_id -- use aliases to avoid dupe name
,s.s_id AS s_s_id
,s."mNrPhone"
,s."dNrPhone"
FROM "Table1" a
JOIN (
SELECT b.s_id, c."mNrPhone", c."dNrPhone", ??.student_id -- misssing!
FROM "Table2" b
JOIN "Table3" c USING (s_id)
WHERE b.a_id = 1001
-- ORDER BY b.last_name -- pointless, DISTINCT will re-order
) s ON a.a_id = s.student_id
WHERE a.k_id = 11211
ORDER BY a.s_id -- first col must agree with DISTINCT ON, could add DESC though
,("mNrPhone" <> '') DESC -- non-empty first
ORDER BY
在同一查询级别上不能与DISTINCT
不一致。要解决此问题,您可以使用GROUP BY
代替,也可以将整个查询放入子查询中,然后在其上运行SELECT
{。}}。
您在子查询中的 ORDER BY
现在已无效。
在这种特殊情况下,如果 - 看起来 - 欺骗只来自子查询(你必须验证),你可以改为:
ORDER BY