使用MySQL提供的Sample數據庫Sakila
現將profiling打開,用來一會查看sql執行時間
set profiling=1;
exists 子查詢與 join聯接效率的對比,功能:查看沒有演員的電影
EXPLAIN SELECT film_id, language_id FROM sakila.film WHERE NOT EXISTS( SELECT * FROM sakila.film_actor WHERE film_actor.film_id = film.film_id );
EXPLAIN SELECT film_id, language_id FROM sakila.film LEFT JOIN sakila.film_actor USING(film_id) WHERE film_actor.actor_id IS NULL;
他們只有一點細微的區別,一個select_type,還有就是Extra里后者用了Not exists,也就是提前終止算法,當遇到第一個actor_id不是null的時候,就舍棄這個電影的篩選.
最后來看看二者的效率
可知使用子查詢Exists的效率要低一些.
SELECT DISTINCT film_id FROM sakila.film JOIN sakila.film_actor USING(film_id); SELECT film_id FROM sakila.film WHERE EXISTS ( SELECT * FROM sakila.film_actor WHERE film.film_id = film_actor.film_id); SHOW PROFILES;
可以看出.依然EXISTS效率要低