🕌
SQLのWHERE EXISTSの使いところを復習する
はじめに
業務でSQLのコードを見ていると、しばしばWHERE EXISTSという構文を見かけます。
対象のサブクエリの結果が真の場合にメインのクエリの結果に追加していくものですが、JOINしてからWHEREで絞りこむのではダメなのでしょうか?
実行結果がよく似た二つの構文ですが、どういう場合に使い分けるのでしょうか?
調べなおしてみました。
JOINだとまずいこと
実はパフォーマンスを求められないのであればWHERE EXISTSはJOINで全てカバーできるようです。
そうすると、じゃあ全部JOINで良くない?って思いますよね。
JOINの方が結果を予想しやすいし書き方も簡単に感じます。
では、なぜ全部JOINだとだめなのか。
・絞り込み条件が複雑な場合はEXISTSの方が簡潔になる。
・JOINだとWHERE句の絞り込みに重複データがあると扱いずらい。
・NOT EXISTSを使う場合はJOINに置き換えるのは大変になる。
といったケースがあるようです。
具体例
JOINの場合
SELECT
r.name
FROM
users u
INNER JOIN
roles r ON u.role_id = r.role_id
WHERE
u.deleted_at IS NULL
AND r.name = 'admin'
AND u.user_id = :user_id
;
EXISTSの場合
SELECT
name
FROM
users
WHERE
users.deleted_at IS NULL
AND EXISTS (
SELECT
users.role_id
FROM
roles
WHERE
users.role_id = roles.role_id
AND name = 'admin'
)
AND user_id = :user_id
上記はどちらも同じ結果になります。
取得したい情報の主体や、読みやすさも選ぶ基準になりそうです。
また、EXISTSの場合は連結しているときと違って、SELECT文のnameが曖昧エラーにならないこともありますね。
おわりに
よく見かける割には、違いのわかりにくい両者ですが、なんとなく掴めてきたでしょうか?
筆者自身、どちらを使うか結構迷うのですが、雰囲気が伝われば幸いです。
株式会社ONE WEDGE
【Serverlessで世の中をもっと楽しく】 ONE WEDGEはServerlessシステム開発を中核技術としてWeb系システム開発、AWS/GCPを利用した業務システム・サービス開発、PWAを用いたモバイル開発、Alexaスキル開発など、元気と技術力を武器にお客様に真摯に向き合う価値創造企業です。
Discussion