从自连接中获得唯一的对,再加上没有匹配项的行

Ada*_*jen 4 sql postgresql left-join duplicates

我在避免查询重复的行时遇到问题,但重复的值会在列之间交替。

我有:

select player_standings.player_ID, matched_player.player_ID 
from player_standings 
left join 
(select player_ID, wins from player_standings) as matched_player 
on matched_player.wins = player_standings.wins 
and matched_player.player_ID != player_standings.player_ID
Run Code Online (Sandbox Code Playgroud)

表格布局player_standings

player_ID serial PRIMARY KEY,
wins int NOT NULL
Run Code Online (Sandbox Code Playgroud)

假设我在以下几行中player_standings

player_id | wins
----------+-------
1253      | 1
1251      | 1
1252      | 0
1250      | 0
1259      | 7
Run Code Online (Sandbox Code Playgroud)

我回来了:

1253, 1251
1252, 1250
1250, 1252  -- reverse dupe
1251, 1253  -- reverse dupe
1259, NULL
Run Code Online (Sandbox Code Playgroud)

我想要的结果是:

1253, 1251
1252, 1250
1259, NULL
Run Code Online (Sandbox Code Playgroud)

Erw*_*ter 5

单程:

SELECT DISTINCT
       GREATEST (p1.player_id, p2.player_id) AS id1
     , LEAST    (p1.player_id, p2.player_id) AS id2
FROM   player_standings p1
LEFT   JOIN  player_standings p2 ON p1.wins = p2.wins
                                AND p1.player_id <> p2.player_id;
Run Code Online (Sandbox Code Playgroud)

其它的办法:

SELECT p1.player_id AS id1, p2.player_id AS id2
FROM   player_standings p1
JOIN   player_standings p2 USING (wins)
WHERE  p1.player_id > p2.player_id;

UNION ALL
SELECT player_id AS id1, NULL::int AS id2
FROM   player_standings p
WHERE  NOT EXISTS (
   SELECT 1
   FROM   player_standings
   WHERE  wins = p.wins
   AND    player_id <> p.player_id
   );
Run Code Online (Sandbox Code Playgroud)

该表达式p1.player_id > p2.player_id排除重复项(除非基表中有重复项)。

UNION ALL 将没有匹配项的每一行添加一次。