2013-01-11 27 views
0

過濾從2個表中的數據的聯合例如起見,讓我們假設3個表:的最佳方式由值在共享第三表

PHYSICAL_ITEM

ID 
SELLER_ID 
NAME 
COST 
DIMENSIONS 
WEIGHT 

DIGITAL_ITEM

ID 
SELLER_ID 
NAME 
COST 
DOWNLOAD_PATH 

賣方

ID 
NAME 

It em ID在兩個項目表中都是唯一的。我想按順序選擇一個給定賣家的所有商品ID。我想出了:

查詢

SELECT PI.ID AS ID, 'PHYSICAL' AS TYPE 
    FROM PHYSICAL_ITEM PI 
     JOIN SELLER S ON PI.SELLER_ID = S.ID 
    WHERE S.NAME = 'name' 
UNION 
SELECT DI.ID AS ID, 'DIGITAL' AS TYPE 
    FROM DIGITAL_ITEM DI 
     JOIN SELLER S ON DI.SELLER_ID = S.ID 
    WHERE S.NAME = 'name' 
    ORDER BY ID 

查詢乙

SELECT ITEM.ID, ITEM.TYPE 
    FROM (SELECT ID, SELLER_ID, 'PHYSICAL' AS TYPE 
       FROM PHYSICAL_ITEM 
      UNION 
      SELECT ID, SELLER_ID, 'DIGITAL' AS TYPE 
       FROM DIGITAL_ITEM) AS ITEM 
     JOIN SELLER ON ITEM.SELLER_ID = SELLER.ID 
    WHERE SELLER.NAME = 'name' 
    ORDER BY ITEM.ID 

查詢,似乎將是最有效的,但它也看起來不必要的重複(2表連接到同一張表,2在同一個表列的where子句)。查詢B對我來說看起來更乾淨(不重複),但由於它有一個子查詢,所以它看起來效率更低。有什麼方法可以讓兩個世界中的最好的,可以這麼說?

+0

你應該測試兩個查詢。第二種可能更好,因爲即使對於視圖而言,Oracle也可以預測推入(例如,假設賣方在[name,id]上有一個索引,它可以選擇先掃描它,謂詞將id推入視圖並加入到兩個工會完成之前的表格[和戈登所說的'union all'就在這裏,因爲這兩個集合由於字面類型而不能合併),第一個可能會掃描賣方兩次。在sqlplus'set autotrace traceonly'中運行並運行每個查詢幾次。請注意每個上使用的運行時和IO。 – DazzaL

回答

0

在這兩種情況下,與union all更換unionUnion不必要地刪除重複項。

我希望查詢更有效率,因爲優化有更多的信息,做加盟(雖然我認爲Oracle是使用索引甚至工會後相當不錯的)時。另外,第一個查詢減少了聯合之前的數據量。

這一點,但是,只有一個意見。真正的測試是定時兩次查詢 - 多次避免緩存填充延遲 - 看看哪個更好。

+0

其實,A是偶數的整個聯盟,還是僅僅是digital_item子查詢?我是否需要在外部選擇包裝才能訂購整套產品? –

+2

訂購整套。在一個工會中,order by只能在陳述的末尾被允許,並且適用於整個集合。 –

+0

實際上,第二個查詢似乎沒有工作......我得到「SQL命令未正確結束」,並且它似乎與子查詢結果的別名有關。 –

相關問題