MySQL 8.4 版本注意事項
MySQL 可以對 col_name IS NULL 執行與 col_name = constant_value 相同的最佳化。例如,MySQL 可以使用索引與範圍來搜尋 NULL 與 IS NULL。
範例
SELECT * FROM tbl_name WHERE key_col IS NULL;
SELECT * FROM tbl_name WHERE key_col <=> NULL;
SELECT * FROM tbl_name
WHERE key_col=const1 OR key_col=const2 OR key_col IS NULL;如果 WHERE 子句包含針對宣告為 NOT NULL 的資料行的 col_name IS NULL 條件,則會將該運算式最佳化移除。當資料行可能產生 NULL 時 (例如,如果它來自 LEFT JOIN 右側的資料表),則不會發生此最佳化。
MySQL 也可以最佳化組合 ,這是在已解析的子查詢中常見的形式。當使用此最佳化時,col_name = expr OR col_name IS NULLEXPLAIN 會顯示 ref_or_null。
此最佳化可以處理任何金鑰部分的其中一個 IS NULL。
假設資料表 t2 的資料行 a 與 b 上有索引,則會最佳化的查詢範例如下
SELECT * FROM t1 WHERE t1.a=expr OR t1.a IS NULL;
SELECT * FROM t1, t2 WHERE t1.a=t2.a OR t2.a IS NULL;
SELECT * FROM t1, t2
WHERE (t1.a=t2.a OR t2.a IS NULL) AND t2.b=t1.b;
SELECT * FROM t1, t2
WHERE t1.a=t2.a AND (t2.b=t1.b OR t2.b IS NULL);
SELECT * FROM t1, t2
WHERE (t1.a=t2.a AND t2.a IS NULL AND ...)
OR (t1.a=t2.a AND t2.a IS NULL AND ...);
ref_or_null 的運作方式是先在參考金鑰上執行讀取,然後針對具有 NULL 金鑰值的列執行個別搜尋。
此最佳化只能處理一個 IS NULL 層級。在下列查詢中,MySQL 只會對運算式 (t1.a=t2.a AND t2.a IS NULL) 使用金鑰查詢,而無法使用 b 上的金鑰部分
SELECT * FROM t1, t2
WHERE (t1.a=t2.a AND t2.a IS NULL)
OR (t1.b=t2.b AND t2.b IS NULL);