SQLクエリの実行順序をゼロから学ぶ

SQLクエリの実行順序をゼロから学ぶ

SQL クエリ ステートメントの実行順序は次のとおりです。

(7)選択 
(8) DISTINCT <選択リスト>
(1)<left_table>から
(3)<結合タイプ> JOIN <右テーブル>
(2)ON <結合条件>
(4) WHERE <where_condition>
(5) GROUP BY <group_by_list>
(6) HAVING <having_condition>
(9) ORDER BY <order_by_condition>
(10) LIMIT <制限数>

事前準備

1. 新しいテストデータベースを作成する

データベース testData を作成します。

2. テスト テーブルを作成し、次のようにデータを挿入します。

ユーザーテーブル


注文フォーム


SQL論理クエリテストステートメントを準備する

a.user_id、COUNT(b.order_id) を total_orders として選択します。
ユーザーからの
LEFT JOINはbとして注文する
a.user_id = b.user_id の場合
ここで、a.city = '北京'
GROUP BY a.user_id
COUNT(b.order_id) < 2 である
ORDER BY total_orders desc

上記の SQL クエリを使用して、注文が 2 件未満の北京の顧客を取得します。

これらの SQL ステートメントの実行中に、SQL ステートメントの実行結果を保存するための仮想テーブルが生成されます。

1. FROMステートメントを実行する

最初のステップは、 FROMステートメントを実行することです。まず、どのテーブルから開始するかを知る必要があります。これは、 FROMによってわかります。現在、 <left_table><right_table>という 2 つのテーブルがありますが、どちらのテーブルから始めるべきでしょうか。それとも、2 つのテーブル間に何らかの接続を作成してから始めるべきでしょうか。それらは互いにどのように関係しているのでしょうか? — デカルト積

FROM ステートメントが 2 つのテーブルに対して直積を実行すると、次の内容を持つ仮想テーブル VT1 (仮想テーブル 1) が取得されます。


合計で 28 件 (ユーザーレコード数 * 注文レコード数) のレコードがあります。これは VT1 の結果です。以下の操作は VT1 に基づいています。

2. ONフィルタリングを実行する

デカルト積を実行した後、 ON a.user_id = b.user_id条件フィルタリングが実行されます。 ONで指定された条件に従って、条件を満たさないデータが削除され、次のように VT2 が得られます。

select * from user as a inner JOIN orders as b ON a.user_id = b.user_id; 


3. 外部行を追加する

このステップは、結合タイプがOUTER JOIN ( LEFT OUTER JOINRIGHT OUTER JOINFULL OUTER JOINなど) の場合にのみ実行されます。ほとんどの場合、 OUTERキーワードは省略しますが、 OUTER外部行の概念を表します。

LEFT OUTER JOIN 、左側のテーブルを予約済みテーブルとしてマークします。つまり、左側のテーブルのすべてのデータが照会され、右側のテーブルに対応するデータがない場合、NULL で埋められます。


RIGHT OUTER JOIN 、右側のテーブルを予約済みテーブルとしてマークします。つまり、右側のテーブルのすべてのデータが照会され、左側のテーブルに対応するデータがない場合、NULL が追加されます。


FULL OUTER JOIN左側のテーブルと右側のテーブルの両方を予約済みテーブルとして使用しますが、MySQL は完全結合をサポートしていません。完全結合は次の方法で実装できます。

準備したテスト SQL クエリ ロジック ステートメントで LEFT JOIN を使用したため、結果の VT3 テーブルは次のようになります。


4. where条件フィルタリングを実行する

外部行が追加されたデータは、where 条件によってフィルタリングされます。<where_condition> 条件を満たすレコードのみがフィルタリングされます。次のように WHERE a.city = 'beijing' を実行して VT4 を取得します。


ただし、WHERE 句を使用する場合は、次の 2 つの点に注意する必要があります。

1. データがまだグループ化されていないため、where フィルター条件で where_condition=MIN(col) を使用してグループ統計をフィルターすることはできません。

2. 列選択操作が実行されていないため、選択で列エイリアスを使用することもできません。たとえば、c='beijing' の場合、table1 から city as c を選択することは許可されません。

5. group byステートメントを実行する

GROU BY句は主に、 WHERE句を使用して取得した仮想テーブルをグループ化するために使用されます。次のように GROUP BY a.user_id を実行して VT5 を取得します。


6. 所有の執行

HAVING句は主にGROUP BY句と組み合わせて使用​​され、グループ化によって得られた VT5 のデータに対して条件付きフィルタリングを実行します。次のように HAVING COUNT(b.order_id) < 2 を実行して VT6 を取得します。


7. リストを選択

SELECT句は今のみ実行されます。最初の行に記述されているからといって、 SELECT句が最初に実行される句であると想定しないでください。

テスト ステートメントでSELECT a.user_id,user_name,COUNT(b.order_id) as total_ordersを実行し、VT6 から必要なコンテンツを選択して、次のように VT7 を取得します。


8. 重複データを排除するためにdistinctを実行する

クエリでDISTINCT句が指定されている場合は、一時的なメモリ内テーブルが作成されます (メモリに収まらない場合は、ディスクに保存する必要があります)。この一時テーブルのテーブル構造は、前の手順で生成された仮想テーブルと同じです。違いは、重複データを排除するために、DISTINCT 操作の列に一意のインデックスが追加されていることです。テスト SQL にはDISTINCT句が含まれていないため、実行されません。

9. order by句を実行する

仮想テーブル VT7 の内容を指定された列で並べ替え、新しい仮想テーブルを返します。テスト SQL ステートメントでORDER BY total_orders DESCを実行すると、次の結果が得られます。

DESCは降順で並び替え、ASCは昇順で並び替えます


10. 制限文を実行する

LIMIT 句は、前の手順で取得した仮想テーブルから指定された位置から指定された行データを選択します。これは、ページングによく使用されます。

MySQLデータベースのLIMITは次のオプションをサポートしています: limit n,m

n 番目のレコードから始まる m 個のレコードを選択することを示します。データが小さい場合は、LIMIT 句を使用しても問題ありません。ただし、データ量が非常に多い場合は、LIMIT n, m を使用することは非常に非効率的です。 LIMIT メカニズムは毎回先頭からスキャンするため、600,000 行目から 3 つのデータを読み取る必要がある場合は、最初に 600,000 行目までスキャンしてから読み取る必要があります。スキャン処理は非常に非効率的な処理です。

以上がこの記事の全内容です。皆様の勉強のお役に立てれば幸いです。また、123WORDPRESS.COM を応援していただければ幸いです。

以下もご興味があるかもしれません:
  • PHP で mysqli を使用して複数の SQL クエリ ステートメントを同時に実行する例
  • MySQLクエリ文の実行プロセスを理解するための記事
  • MySQLでSQLクエリ文がどのように実行されるかを分析する
  • Mysql系SQLクエリ文の書き順と実行順を詳しく解説
  • MySQL では SQL クエリはどのように実行されますか?
  • SQLクエリステートメントの実行プロセス

<<:  Dockerイメージの階層化の原理の詳細な説明

>>:  vue プロジェクトで rem を使用して px を置き換える例

推薦する

Linuxアカウントファイル制御管理の詳細な手順

Linux システムでは、ユーザーが手動で作成したさまざまなアカウントに加えて、システムまたはプログ...

MySQL テーブルデータのインポートとエクスポートの例

この記事では、MySQL テーブル データのインポートおよびエクスポート操作について説明します。ご参...

HTML テーブルインライン形式の詳細な説明

インライン形式<colgroup>...</colgroup>属性名 属性値...

Vueはボトムクエリ関数を実装します

この記事では、ボトムクエリ機能を実装するためのVueの具体的なコードを例として紹介します。具体的な内...

MySQLデータベース監視binlogを有効にする手順

序文多くの場合、ユーザーが自分のデータに対して実行する操作に基づいて何かを行う必要があります。たとえ...

単一のMySQLテーブルを復元する手順

休憩中に、眠気を完全に吹き飛ばす電話がかかってきました。「開発者が更新 SQL を書くときに whe...

MySQL 数千万のビッグデータに対するSQLクエリ最適化の知識ポイントのまとめ

1. クエリを最適化するには、テーブル全体のスキャンを避けてください。まず、where と orde...

イメージのパッケージ化とワンクリック展開を実現するためにDockerを組み合わせたアイデア

1. サーバーにDockerをインストールする yumでdockerをインストール設定ファイルを変更...

Vueのハッシュジャンプ原理の詳細な説明

目次ハッシュと履歴の違いハッシュ履歴getCurrentLocation の実装setupListe...

Mysql を 5.7 にアップグレードした後のグループ クエリの問題を解決する

問題を見つける最近MySQLをMySQL 5.7にアップグレードした後、次のようなクエリでグループ化...

Vue のレスポンシブ原則と双方向データの詳細な分析

応答性を実現するための object.defineProperty の理解observe/watch...

nginx アンチホットリンクおよびアンチクローラー設定の詳細な説明

新しい設定ファイルを作成します (たとえば、nginx インストール ディレクトリの下の conf ...

MySQL マスタースレーブスイッチチャネルの問題の解決策

VIP を設定した後、アクティブ/スタンバイの切り替え中に表示されるエラー メッセージは次のとおりで...

docker compose サービスの起動順序を制御する方法

まとめDocker-compose は複数の Docker コンテナ サービスを簡単に組み合わせるこ...

Linux システムで Centos7 を使って ElasticSearch ミドルウェアと共通インターフェースを構築するデモ

1. ミドルウェアの紹介1. 基本概念ElasticSearch は Lucene をベースにした検...