2013-04-18 178 views
2

table A, B and CSQL - 相關子查詢

我要回表A中不表B和該列表中存在的所有條目表不存在C.

select * from table_A as a 
where not exists (select 1 from table_B as b 
where a.id = b.id) 
的多層

這讓我在一個不在B.條目的第一個結果但現在我想只有那些還沒有C.

我試過的口味的這個結果的條目:

select * from table_A as a 
where not exists (select 1 from table_B as b 
where a.id = b.id) 
AND 
where not exists (select 1 from table_C as c 
where a.id = c.id) 

但這不是正確的邏輯。如果有一種方法可以存儲來自第一個查詢的結果,然後從表C中不存在的結果中選擇*,但我不確定該怎麼做。我很感激幫助。

+1

你使用什麼數據庫系統演示? –

+0

我正在使用MS sql – codingknob

回答

2

在第二個查詢的(外部部分)中有兩個WHERE子句。這不是有效的SQL。如果你刪除它,它應該按預期工作:

select * from table_A as a 
where not exists (select 1 from table_B as b 
        where a.id = b.id) 
AND 
     not exists (select 1 from table_C as c   -- WHERE removed 
        where a.id = c.id) ; 

測試中SQL-Fiddle(日Thnx @Alexander)

2

怎麼樣使用LEFT JOIN

SELECT a.* 
FROM TableA a 
     LEFT JOIN TableB b 
      ON a.ID = b.ID 
     LEFT JOIN TableC c 
      ON a.ID = c.ID 
WHERE b.ID IS NULL AND 
     c.ID IS NULL 
3

試試這個:

select * from (
    select a.*, b.id as b_id, c.id as c_id 
    from table_A as a 
    left outer join table_B as b on a.id = b.id 
    left outer join table_C as c on c.id = a.id 
) T 
where b_id is null 
    and c_id is null 

另一種實現是這樣的:

select a1.* 
from table_A as a1 
inner join (
    select a.id from table_A 
    except 
    select b.id from table_B 
    except 
    select c.id from table_c 
) as a2 on a1.id = a2.id 

請注意如here所述的子查詢形式的限制。第二個實現,通過最簡潔明確地描述SQL Server所需的操作,可能是最有效的。

1

我不喜歡「不存在」,但如果由於某種原因,它似乎更符合你的邏輯;那麼你可以爲你的第一個查詢使用別名。隨後,您可以重新應用另一個「不存在」子句。例如:

SELECT * FROM 
    (select * from tableA as a 
    where not exists (select 1 from tableB as b 
    where a.id = b.id)) 
AS A_NOT_IN_B 
WHERE NOT EXISTS (
    SELECT 1 FROM tableC as c 
    WHERE c.id = A_NOT_IN_B.id 
) 
2

有沒有一個更選項存在於SQLFiddle

操作

SELECT * 
FROM dbo.test71 a 
WHERE NOT EXISTS(
       SELECT 1 
       FROM (SELECT b.ID 
         FROM dbo.test72 b 
         UNION ALL 
         SELECT c.ID 
         FROM dbo.test73 c) x 
       WHERE a.ID = x.ID 
       ) 

演示

從@ ypercube的選項。謝謝你目前;)

SELECT * 
FROM dbo.test71 a 
WHERE NOT EXISTS(
       SELECT 1 
       FROM dbo.test72 b 
       WHERE a.ID = b.ID 
       UNION ALL 
       SELECT 1 
       FROM dbo.test73 c 
       WHERE a.ID = c.ID 
       ); 

SQLFiddle

+1

不錯。您也可以在答案中添加此變體:[SQL-Fiddle](http://sqlfiddle.com/#!3/b10f3/3) –