ベストアンサー
結合とサブクエリの両方がSQLステートメントに配置されますが、私は常に結合のみを使用してクエリを記述しようとします。一方、サブクエリを導入するのは、サブクエリがないと必要なデータを取得できない場合のみです。
その理由は、結合の実行が速くなる傾向があるためです。実際、結合を使用したクエリの取得時間は、ほとんどの場合、サブクエリよりも高速であると言えます。
その理由は、結合によって計算の負担が軽減されるためです。複数のクエリを1つの結合クエリに置き換えることでデータベースを作成します。これにより、レコードを検索、フィルタリング、および並べ替えるデータベースの機能がより有効に活用されます。
もちろん、クエリに結合を追加すると、データベースサーバーはより多くの作業を行う必要があります。データの取得時間を遅くします。
正規化されたデータベースからデータを取得するには結合が必要ですが、結合が正しくないとパフォーマンスが大幅に低下し、クエリ結果が不正確になる可能性があるため、結合を正しく書き込むことが重要です。
場合によっては、サブクエリによって複雑な結合や和集合が置き換えられ、パフォーマンスへの悪影響は最小限に抑えられます。
サブクエリの例
サブクエリを使用して実際に回避できない場合があります。 MySQL用のSakilaサンプルデータベースと私の Navicat データベース開発および管理クライアントを使用したいくつかの例を次に示します。
例1:JOIN句の一部として集計関数を使用する
ほとんどの場合、テーブルは共通のフィールドで結合されます。実際、同じデータであることを示すために、共通フィールドが同じ名前を共有することも珍しくありません。ただし、次のクエリでは、customerテーブルが最新(MAX)のcreate\_dateに結合されているため、クエリ結果は最後にサインアップした顧客のものになります。
集計関数を使用できないため、サブクエリが使用されます。 WHERE句の一部として。この独創的な回避策は、その制限を回避します!
例2:
このクエリでは、サブクエリを使用して中間結果セットをフェッチし、レンタルした映画のCOUNTにAVG()関数を適用できるようにします。これは、別の(COUNT)の結果に集計(AVG)を適用しているため、私が二重集計と呼んでいます。
この特定のクエリは非常に高速で、0.044秒しかかかりません。単一の値。通常、最も遅いクエリは、全表スキャンを必要とするクエリです。
質問に答えることを願っています。
よろしくお願いいたします。
アダム
回答
通常 クエリはできるだけ明確に記述し、最適化はRDBMSのクエリプロセッサと、物理設計の調整を担当するDBA(ある場合)に任せる必要があります。ほとんどの場合、十分なパフォーマンスが得られるはずですが、例外もあります。RDBMSのクエリオプティマイザに死角や悪いケースがある場合があります。
ここで、結合またはサブクエリのいずれかが問題になる場合オプティマイザーの場合、サブクエリに含まれる可能性がはるかに高くなります。これは、結合がすべてのユーザーが使用する言語の基本機能であるのに対し、多くのユーザーはサブクエリをまったく使用しないためです。Sybaseからアプリを変換することでわかりました。 Microsoftのバグのため、SQLServerに多くのサブクエリを結合として書き直す必要がありました。サブクエリの処理-非常に特殊な場合(サブクエリのwhere句にバインドされたパラメータが含まれている場合)ですが。 SQL Serverの顧客の多くが、サブクエリではなく結合を自然に生成するMicrosoftのグラフィカルクエリエディタでSQL Serverを使用しているため、SQLServerにサブクエリにバグがあったことは驚くことではありません。
通常、時期尚早の最適化はお勧めしません。ただし、ここでは例外を設けます。アプリケーションを複数のデータベースプラットフォーム間で移植可能にする必要がある場合は、サブクエリでバグやオプティマイザの選択が不適切になる可能性が高いため、ほとんどの場合、サブクエリへの結合をお勧めします。アプリケーションは移植可能である必要はありません。最も自然な方法でクエリを記述し、問題がなければ(ほとんどの場合)問題ありません。問題がある場合は、クエリを別の方法で書き直して、それが役立つかどうかを確認します。また、DBAをお持ちの場合は、パフォーマンスの問題について彼に相談してください。