我有36萬記錄的表和這裏的兩個索引字段進行查詢:使用JOIN'ed映射表比同一個表中的多個字段更好嗎?
SELECT COUNT(*)
FROM emails
WHERE
department_id IN(1,2,3,4)
AND category_id IN (5,6,7,8)
(Time: 0.9624802)
id: 1
select_type: SIMPLE
table: emails
type: range
possible_keys: emails_department_id_idx,emails_category_id_idx
key: emails_category_id_idx
key_len: 5
ref: NULL
rows: 54018
Extra: Using where
所以只有一個索引被使用在那裏。 (當使用更簡單的比較或範圍標準時,我可以獲得索引合併的工作,但是我需要根據ID列表進行這種檢查)。
在這裏,我創建了兩個新表映射這種關係,並使用JOIN的我複製了相同的結果:
SELECT COUNT(*)
FROM emails
LEFT JOIN email_to_department ON (email_to_department.email_id = emails.id AND email_to_department.department_id IN (1,2,3,4))
LEFT JOIN email_to_category ON (email_to_category.email_id = emails.id AND email_to_category.category_id IN (5,6,7,8))
WHERE
email_to_department.department_id IS NOT NULL
AND email_to_category.category_id IS NOT NULL
(Time: 0.5217777)
*************************** 1. row ***************************
id: 1
select_type: SIMPLE
table: email_to_category
type: range
possible_keys: PRIMARY,category_id
key: category_id
key_len: 4
ref: NULL
rows: 61282
Extra: Using where; Using index
*************************** 2. row ***************************
id: 1
select_type: SIMPLE
table: email_to_department
type: ref
possible_keys: PRIMARY,department_id
key: PRIMARY
key_len: 4
ref: testdb.email_to_category.email_id
rows: 1
Extra: Using where; Using index
*************************** 3. row ***************************
id: 1
select_type: SIMPLE
table: emails
type: eq_ref
possible_keys: PRIMARY
key: PRIMARY
key_len: 4
ref: testdb.email_to_category.email_id
rows: 1
Extra: Using index
3 rows in set (0.38 sec)
所以每個查詢現在使用的指標,並修剪幾乎一半的時間了。這是不好的設計?我應該以同樣的方式寫下其餘的這些關係嗎?
如果我以相同的方式添加更多條件,JOIN'd版本的查詢似乎變得更快,另一個保持大致相同。
上做只是一個單一的索引字段一個簡單的查詢是非常非常快,當然:
SELECT COUNT(*)
FROM emails
WHERE department_id IN(1,2,3,4)
是否有另一種策略,我可以使用,使這些類型的查詢速度還是?還有其他一些屬性需要進行過濾以及以不同的組合方式進行過濾,因此創建多列索引並不會真正起到幫助作用。
在您的第一個查詢中,您可能希望考慮在department_id和category_id上添加一個關鍵字INDEX(department_id,category_id)。這將有助於使用索引的第一個查詢過濾器結果。 – JamesHalsall