2008-12-02 51 views
2

我有以下五個表:只讀取匹配連接表(SQL)的所有條目的行

  • ISP
  • 產品
  • 連接
  • 附加元件
  • 附加元件/產品(數據透視表用於多對多關係)。

每個產品都鏈接到ISP,每個連接都列在產品中。通過使用數據透視表(每個產品只有2個字段,一個用於產品ID,一個用於AddOn ID),每個產品都可以有多個附加組件。

我感興趣的結果是與所列出的插件的每個連接(我正在使用MySQL的GROUP_CONCAT爲此創建插件的名稱字段的逗號分隔列表)。這工作得很好原樣,查詢看起來是這樣的:

SELECT i.name AS ispname, i.img_link, c.download, c.upload, c.monthly_price, c.link, 
GROUP_CONCAT(a.name) AS addons, SUM(pa.monthly_fee) AS addon_price 
FROM isp i JOIN product p ON i.id = p.isp_id 
JOIN `connection` c ON p.id = c.product_id LEFT JOIN product_addon pa ON pa.product_id = p.id AND pa.forced = 0 
LEFT JOIN addon a ON pa.addon_id = a.id GROUP BY c.id 

我使用LEFT任命爲有可能的產品都沒有插件。

我的問題是,有可能選擇列出的連接必須具有的一些插件,呈現爲插件ID列表,如(1,14,237)。如果我將它作爲JOIN語句(AND pa.addon_id IN(...))中的附加條件放入,它將返回僅包含一個所列插件的所有連接,但不一定包含所有連接。

是否有某種方式可以返回所有連接:最小有所有的插件(它們可以有額外的)通過SQL?

回答

2
GROUP BY set-of-column 
HAVING SUM(CASE WHEN ISNULL(pa.addon_id, 0) IN (1,14,237) THEN 1 ELSE 0 END) = 3 
0

您可以添加到WHERE子句:

AND NOT EXISTS (SELECT NULL FROM addon a2 
       WHERE a2.addon_id IN (1,14,237) 
       AND NOT EXISTS 
       (SELECT NULL 
        FROM product_addon pa2 
        WHERE pa2.addon_id = a2.addon_id 
        AND pa2.product_id = p.product_id 
       ) 
       ) 

或等價:

AND NOT EXISTS (SELECT NULL FROM addon a2 
       LEFT JOIN product_addon pa2 
        ON pa2.addon_id = a2.addon_id 
       AND pa2.product_id = p.product_id 
       WHERE a2.addon_id IN (1,14,237) 
       AND pa2.product_id IS NULL 
       ) 
       ) 
相關問題