Postgresql
跨連接進行 ORing 時 Postgres 不使用索引
我正在對兩個表進行連接查詢,我需要在每個表中的欄位上執行 ILIKE 過濾器,兩端都帶有萬用字元,如果它們中的任何一個匹配,它應該返回一行。
大約:
SELECT * FROM "tableA" LEFT OUTER JOIN "tableB" ON "tableA"."tableB_id" = "tableB"."id" WHERE "tableA"."name" ILIKE '%rich%' OR "tableB"."name" ILIKE '%rich%';
由於這兩個表都很大,我決定嘗試使用三元組索引來加快速度。但是,這似乎沒有幫助,並且在進行了 EXPLAIN ANALYZE 之後,我發現沒有使用索引。如果過濾器與 AND 而不是 OR 組合使用,則使用它們,如果我在同一個表中的兩個索引列之間執行 OR,而不是在不同表中的索引列之間執行 OR,則使用它們。
任何人有任何想法為什麼?
有時將帶有
OR
條件的查詢重寫為UNION
(ALL
) 查詢很有用。這通常會導致可能更有效的不同執行計劃。測試將確定兩種方法/計劃中的哪一種在每種情況下更有效(例如,如果三元索引用於聯合的兩個部分)。重寫:
SELECT * FROM "tableA" AS a LEFT OUTER JOIN "tableB" AS b ON a."tableB_id" = b."id" WHERE a."name" ILIKE '%rich%' UNION ALL SELECT * FROM "tableA" AS a INNER JOIN "tableB" AS b ON a."tableB_id" = b."id" WHERE b."name" ILIKE '%rich%' AND (a."name" IS NULL OR a."name" NOT ILIKE '%rich%') ;