2012-07-23 41 views
1

我遇到了InnoDB mysql數據庫問題。例如,我有兩個表,事件和events_artists具有以下結構:Mysql查詢頭腦遲鈍

events: 
id (PK) 
host_id 
date 

events_artists: 
id (PK) 
event_id 
artist_id 

表事件有10萬項,events_artists持有約150,000。

我必須做的事情之一是檢查表中events_artists中未引用的表事件中的條目。要做到這一點,在另一篇文章中,我收到了查詢

SELECT * FROM events WHERE id IS NULL OR id NOT IN (SELECT event_id FROM events_artists) 

從邏輯上看,這個查詢看起來不錯。但是,它只是極其慢。我現在讓它運行一個小時,但仍然沒有結果。那裏有一些事情是錯的。

我很感激任何關於如何優化的幫助!

感謝

查爾斯

發現的解決方案

下面的查詢,使語句要快得多:

SELECT * 
FROM events a 
    LEFT JOIN events_artists b 
    ON a.id = b.event_id 
    WHERE b.event_id IS NULL; 

然而,主要的速度提升是加入外鍵。我不得不在過渡期間刪除它們以進行重複搜索,並將它們添加回來,這會提高速度。雖然查詢花了一個多小時,但現在只需要一秒

謝謝!

Charles

+0

是什麼'EXPLAIN <你的選擇查詢的位置>'說什麼? – DCoder 2012-07-23 09:54:05

回答

3

爲了獲得更快的結果,您應該避免使用子查詢。或者,您可以嘗試使用LEFT JOIN獲取事件中的記錄,但不能獲取events_artists中的記錄。

訪問Visual explanation of joins

SELECT * 
FROM events a 
    LEFT JOIN events_artists b 
     ON a.id = b.event_id 
WHERE b.event_id IS NULL; 

另外,還要確保你對列ID和事項標識指數更快的查詢執行。

+0

謝謝,Omesh!我用你的解決方案和另一個編輯更新了這個問題。也感謝偉大的鏈接! – weltschmerz 2012-07-23 13:01:44

+0

非常歡迎您! – Omesh 2012-07-23 13:08:40

1

如果您運行查詢的EXPLAIN,您會看到子查詢被視爲DEPENDENT,這意味着它將在events表中針對每行運行一次,因此速度很慢。

你可以改變它,像這樣獨立:

SELECT events.* 
FROM events 
LEFT JOIN events_artists ON (events.id = events_artists.event_id) 
WHERE events_artists.event_id IS NULL 
1

試試這個

select 
    ev.* from events as ev 
    left join events_artists as ea on ev.id=ea.event_id 
where 
    ea.event_id is null or ev.id is null