我需要幫助,在一個LEFT JOIN
的SQL查詢中選擇正確的索引。MySQL查詢優化:正確索引
我有兩個表(對象和月度報告):
CREATE TABLE some_objects (
id int(11) NOT NULL AUTO_INCREMENT,
...,
PRIMARY KEY (id),
);
CREATE TABLE month_reports (
id int(11) NOT NULL AUTO_INCREMENT,
some_object_id int(11) DEFAULT NULL,
month int(11) NOT NULL,
year int(11) NOT NULL,
...,
PRIMARY KEY (id),
INDEX IDX_123 (month, year),
INDEX IDX_456 (some_object_id),
INDEX IDX_789 (some_object_id, month, year),
CONSTRAINT FK_123 FOREIGN KEY (some_object_id)
REFERENCES some_objects (id) ON DELETE RESTRICT ON UPDATE RESTRICT
)
我需要選擇與特定月份或沒有他們報告的所有對象。我想這個查詢:
SELECT * FROM some_objects so
LEFT JOIN month_reports mr ON mr.some_object_id = so.id
WHERE
mr.month = :month
AND mr.year = :year
OR mr.id IS NULL
EXPLAIN
結果:
id select_type table type possible_keys
1 SIMPLE so ALL
1 SIMPLE mr ALL IDX_456,IDX_789
EXPLAIN
結果,而不OR mr.id IS NULL
:
id select_type table type possible_keys key ref
1 SIMPLE mr ref IDX_123,IDX_456,IDX_789 IDX_123 const,const
1 SIMPLE so eq_ref PRIMARY
但是,如果沒有OR mr.id IS NULL
我不無報告得到的對象!
我應該添加哪個其他索引?我是否需要更改查詢?
P.S.對不起我的英語不好。
UPD。ANALYZE TABLE
返回「狀態正常」。 EXPLAIN
結果與FORCE INDEX
(10個對象,只有一個有報告):
id select_type table type possible_keys key rows
1 SIMPLE so ALL 10
1 SIMPLE mr ref IDX_789 IDX_789 1
您可以添加'some_object_id'現有'IDX_123'。 – Vatev
@Vatev對不起,我修正了IDX_789。它具有some_object_id,month,year列,並且它不被MySQL服務器使用:( –
它有時候會在你的行數太少時添加一些數據(如果數量很少,請添加一些)嘗試運行[ANALYZE TABLE](https:// dev.mysql.com/doc/refman/5.7/en/analyze-table.html)如果這樣做不起作用,可以在JOIN中添加'FORCE KEY(IDX_789)'併發布查詢計劃。 – Vatev