2012-03-13 58 views
2

我發現,雖然編寫查詢的表現,這是原來的查詢(BTW 我使用MySQL 5.5.8)奇怪的慢行爲IN子句SQL

我需要做的是選擇id, a, b c,d從所有元素(和元素的所有ocurrences)有現在2012-03-13 10:41:34.8431(EG)之間插入一個時間(time)新的元組也是屬性,這些元素必須有一些ocurrences的HAVING COUNT(id) >= '5'

SELECT id, a, b, c,d FROM table1 WHERE 
id IN (SELECT id FROM table1 WHERE id IN (SELECT id FROM 
table1 WHERE time >= '2012-03-13 10:41:34.8431' AND a = '1') HAVING COUNT(id) >= '5') 

table1有aprox 700元組。該查詢持續14.5s

由於這是不能接受藉此長時間,我都分開只是querys測試:

SELECT id FROM table1 WHERE id IN (SELECT id FROM 
table1 WHERE time >= '2012-03-13 10:41:34.8431' AND a = '1') HAVING COUNT(id) >= '5' 

注意到0.025s,並返回一個元組id = 6
由於我知道結果,只是爲了測試我執行了查詢的另一部分:

SELECT id, a, b, c,d FROM table1 WHERE id IN (6) 

並花了0.0012s

現在,會發生什麼呢?我不知道,只是一些毫無根據的猜測。爲什麼他們之間有如此多的區別?
如果這是正常的,是否有任何已知的workarrounds?

+1

你能添加一個「explain」嗎? – 2012-03-13 12:43:23

+2

你爲什麼在做「哪裏有身份證」?你不能把它當作一個查詢嗎? – 2012-03-13 12:44:01

+1

嘗試此查詢'SELECT ID,a,b,c,d FROM table1 WHERE id IN(SELECT id FROM table1 WHERE time> ='2012-03-13 10:41:34.8431'AND a ='1')HAVING COUNT(id)> ='5' ' – 2012-03-13 12:48:52

回答

4

我會扭轉這種局面......開始你是合格ID列表,然後用它來加入到原始表來獲取數據。凡子選擇總是表現根命中

SELECT 
     T1.id, 
     T1.a, 
     T1.b, 
     T1.c, 
     T1.d 
    FROM 
     (SELECT id, count(*) 
      FROM table1 
      WHERE a = 1 
      AND time >= '2012-03-13 10:41:34.8431' 
      group by id 
      having count(*) > 4) as PreQualified 
     JOIN table1 T1 
     ON PreQualified.ID = T1.ID 
     AND T1.a = 1 
     AND T1.time >= '2012-03-13 10:41:34.8431' 

我重新申請同一標準的JOIN子句,因爲我不知道這個數據的其餘部分。由於我不知道你是否可以有一個比指示的時間有前時間ID和要排除那些太,但保留的前提下,ID必須至少有「= 1」,上/指定的時間段之後。

由於只使用ID的預篩選/合格名單開始,你不必參加所有其他ID,然後扔出來時,他們的總數是遠遠不夠的。

每從阿米輸入,我用他的背景下,以澄清依賴查詢...

應查看您的查詢的EXPLAIN結果來確定,如果你的查詢正在運行的子查詢外的每一行查詢,它將作爲依賴性查詢出現在您的EXPLAIN結果中。

通過加入它,您可以經常將依賴子查詢轉換爲DERIVED表,正如此處所做的那樣。

3

對於執行內部查詢在外部查詢的每一行:(

「的差的典型情況中的子查詢性能是當子查詢返回少量的行,但外部查詢返回大量的行與子查詢結果進行比較。

問題是,對於使用IN子查詢的語句,優化程序將其重寫爲相關的子查詢。 '

from http://dev.mysql.com/doc/refman/5.0/en/subquery-restrictions.html

+0

爲什麼以這種方式定義IN,爲什麼每次都執行內部查詢? – eversor 2012-03-14 11:13:38

+0

它只是優化器在mysql中的工作方式。 – 2012-03-16 07:18:30