2012-12-18 76 views
2

我絕對不擅長MySQL,但直到現在我還沒有。我正在處理一個大型數據庫,特別是一個具有1500多行的用戶表。所以我需要弄清楚如何有效地完成我用IN子句完成的工作。MySQL中的高效子查詢

這裏的查詢:

SELECT * 
FROM artists_profile 
WHERE artist_name LIKE '%$test%' OR id IN (SELECT profile_id 
       FROM artists_profileltp_join 
      WHERE genre_id IN (SELECT id 
           FROM artists_ltp 
           WHERE genre LIKE '%$test%') OR 
            details LIKE '%$test%') 

數據庫樣本數據

artists_profile   artists_profileltp_join 
+------+-------------+  +---------+------------+---------+ 
| ID | artist_name |  |genre_id | profile_id | details | 
+------+-------------+  +---------+------------+---------+ 
| 1 | Jake  |  |  1 |  2 | rap  | 
| 2 | Obama  |  |  2 |  3 | smooth | 
| 3 | Bob   |  |  1 |  1 | metal | 
+------+-------------+  +---------+------------+---------+ 
    artists_ltp 
+------+-------+ 
| ID | genre | 
+------+-------+ 
| 1 | rock | 
| 2 | jazz | 
+------+-------+ 

爲$測試= 「JA」 將返回artist_profile ID 1和3,因爲傑克與 「JA」 開頭期望的結果和鮑勃扮演包含「ja」的流派。

表格很簡單。

Artists_profile包含有關用戶的所有獨特信息。 Artists_profileltp_join具有profile_id(int(11)),genre_id(int(11))和詳細信息(varchar(200))字段,並簡單地將artists_profile表連接到artists_ltp表。

artists_ltp只有一個唯一的ID和varchar(50)字段。平均需要30秒來運行我的查詢。我可以做些什麼來加快速度並提高子查詢的效率?

回答

3
SELECT DISTINCT a.* 
FROM artist_profile a 
     INNER JOIN artists_profileltp b 
      ON a.ID = b.profile_ID 
     INNER JOIN artists_ltp c 
      ON b.genre_id = c.id 
WHERE c.genre LIKE '%$test%' OR 
     c.details LIKE '%$test%' 

JOIN在這一個會更好。但不幸的是,由於您使用的是LIKE,因此您查詢的內容不會使用INDEX。我會建議你閱讀FULL TEXT SEARCH

一件事一些文章,查詢與SQL Injection脆弱的,請閱讀下面的文章,以瞭解如何從中阻止,

+0

打敗了我......只有我想提出的其他優化是從C中選擇,加入B,加入A –

+0

非常感謝!這很好。但是,如何返回artist_profile?該查詢從所有三個表中返回行。 – Colin

+0

另一個問題...從artist_profile行不一定需要鏈接到其他表,我仍然希望這些被返回...我更新了原始查詢,以顯示我的意思。 – Colin