2014-03-19 163 views
0

我試圖創建一個SELECT查詢以通過某些過濾器獲取產品。您可以在下面的屏幕上看到DB結構。 DB structure definitions - 產品類型,features - 產品功能(例如價格,大小,顏色),significations - 價值上的一些特點,objects - 現場avalible產品,trans_obj2sign - 輔助表以多對多的關係。Mysql查詢以通過過濾器選擇產品

我使用PHP的考慮選擇過濾器創建查詢:

SELECT o.id, o.name, o.url, GROUP_CONCAT(f.name separator '--|||--') as feature_name,  GROUP_CONCAT(f.title separator '--|||--') as feature_title, GROUP_CONCAT(s.value separator '--|||--') as signification_value 
FROM objects as o 
JOIN trans_obj2sign o2s ON o.id=o2s.object_id 
JOIN features f ON o2s.feature_id=f.id 
JOIN significations s ON o2s.signification_id=s.id 
WHERE o.id IN (
    SELECT o2s.object_id 
    FROM trans_obj2sign o2s 
    JOIN significations s ON (o2s.signification_id = s.id) 
    WHERE (
    (s.id IN ("2", "43", "48", "55") AND s.feature =13) 
    OR (s.id IN ("14", "23", "49", "52") AND s.feature =14) 
    OR (s.value BETWEEN 0 AND 500 AND s.feature =17) 
    ) 
    GROUP BY o2s.object_id 
    HAVING COUNT(o2s.object_id) =3 
) 
GROUP BY o.id 
LIMIT 0, 50 

內部查詢返回一個significations的態度對待所有過濾器對象的ID。主查詢返回所需的產品屬性。

的問題是:

  1. 我可以重寫此查詢執行得更快? (這個很重)
  2. 我應該添加哪些索引?
  3. 如何添加ORDER BY某些含義值。類似於WHERE s.feature=17 ORDER BY s.value(假設s.feature = 17是產品價格)

回答

1

擺脫IN +子查詢。只需將它移動到FROM部分即可執行一次。

像這樣

SELECT o.id, o.name, o.url, GROUP_CONCAT(f.name separator '--|||--') as feature_name,  GROUP_CONCAT(f.title separator '--|||--') as feature_title, GROUP_CONCAT(s.value separator '--|||--') as signification_value 
FROM objects as o 
JOIN trans_obj2sign o2s ON o.id=o2s.object_id 
JOIN features f ON o2s.feature_id=f.id 
JOIN significations s ON o2s.signification_id=s.id 
JOIN (
    SELECT o2s.object_id 
    FROM trans_obj2sign o2s 
    JOIN significations s ON (o2s.signification_id = s.id) 
    WHERE (
    (s.id IN ("2", "43", "48", "55") AND s.feature =13) 
    OR (s.id IN ("14", "23", "49", "52") AND s.feature =14) 
    OR (s.value BETWEEN 0 AND 500 AND s.feature =17) 
    ) 
    GROUP BY o2s.object_id 
    HAVING COUNT(o2s.object_id) =3 
) filtered on filtered.id=o.id 
GROUP BY o.id 
LIMIT 0, 50 

添加索引其在所使用的字段。

要添加ORDER BY地方查詢的FROM部分(如子查詢),並使用ORDER BY

+0

了你在第一次2個問題。但是對於3rd:我在結果查詢中沒有字段'price'來執行'ORDER BY'。我不能在GROUP BY語句前添加'WHERE s.feature = 17 ORDER BY s.value'。 –

+0

爲什麼你不能添加WHERE部分?當然可以。在ORDER BY中使用的選定字段列表中包含任何文件 – StanislavL