十分に最適化されていない、またはパフォーマンスが極端に低い SQL ステートメントに直面した場合、通常は、クエリ結果セットが元のものと同じになるように SQL ステートメントをリファクタリングし、SQL パフォーマンスが向上することを期待します。 SQL をリファクタリングする場合、一般的には参照できる特定の方法とテクニックがあります。この記事では、これらのテクニックと方法を使用して SQL をリファクタリングする方法を紹介します。 1. SQLの分解 複雑な SQL の場合、最初に考えるのは、同じビジネス処理結果を得るために、複雑な SQL を複数の単純な SQL に分解する必要があるかどうかです。 これまで、データベース層が可能な限り多くの作業を完了する必要性は常に強調されてきました。そのため、一部の古い製品やプロジェクトで非常に複雑で非常に長い SQL ステートメントを頻繁に目にする理由を理解するのは難しくありません。以前は、これを行うロジックには複数のインタラクションが必要であると考えられていましたが、これはネットワーク帯域幅、プログラムとデータベース間のネットワーク通信などの点で非常にコストのかかるものでした。今では、帯域幅や遅延の面でも、ネットワーク速度は以前よりもはるかに速くなり、複数のやり取りでも大きな問題は発生しません。汎用サーバーでも1秒あたり10万件以上のクエリを実行できるため、複数の小さなクエリを実行しても大きな問題にはなりません。 複雑な SQL ステートメントを分解すると、非常に複雑な SQL ステートメントを処理するときにパフォーマンスが大幅に向上します。したがって、非常に複雑な SQL ステートメントに直面し、パフォーマンスの問題が発生する場合は、最適化のために小さなクエリに分割することをお勧めします。 ただし、アプリケーションを設計する際に、クエリが十分でパフォーマンス上の問題が発生しない場合は、少し複雑な SQL で完了できます。複数の小さなクエリに厳密に分割するのは賢明ではありません。 今日の多くの高性能アプリケーション システムでは、複雑なビジネスのクエリ要件を満たすために、単一テーブル操作を使用し、アプリケーション内で単一テーブルのクエリ結果を関連付けることが強く推奨されています。 1 つの SQL ステートメントで同じ作業を実行できる場合、なぜ別々の SQL ステートメントを記述するのでしょうか。また、アプリケーションで SQL クエリを複数回実行し、結果セットを関連付けるのはなぜでしょうか。なぜこれを行う必要があるのでしょうか。 一見すると、これは複雑でメリットがないように見えます。単一のクエリではなく、複数のクエリになります。実際、この分解には次のような利点があります。
2. クエリのセグメンテーション 場合によっては、大規模なクエリ、つまり結果セットが大きいクエリの場合、「分割統治」の考え方を採用し、大規模なクエリを小さなクエリに分割する必要があります。各クエリはまったく同じ機能を持ちますが、小さな部分のみを完了し、毎回クエリ結果の小さな部分のみを返します。簡単に言えば、WHERE 条件のフィルタリング範囲を分割し、毎回データの一部のみをクエリすることであり、ページング クエリに似ています。 そうすることで、SQL クエリ自体と上位レベルのサービスの両方に対して、ごくわずかなオーバーヘッドしか発生しなくなります。最も典型的なケースはページングクエリであり、MyBatis などのさまざまなフレームワークで十分にサポートされています。実際の使用時に少し注意を払うだけで回避できます。 3. 実行計画 実行プランで EXPLAIN キーワードを使用すると、MySQL が SQL ステートメントをどのように実行するかを知ることができ、クエリ ステートメントまたはテーブル構造のパフォーマンスのボトルネックを分析するのに役立ちます。 EXPLAIN のクエリ結果では、インデックスの主キーがどのように使用されているか、データ テーブルがどのように検索またはソートされているかなどもわかります。 構文の形式は次のとおりです。
実行プランの結果は、インデックスの追加、インデックス順序の調整、特定の関数の使用回避など、SQL ステートメントをさらに再構築するためのガイドとなります。 実行計画については、以降の章で詳しく説明します。 IV. 原則の遵守 日常的に SQL を記述するときに、良い習慣を身につけて注意を払うと、SQL パフォーマンスの問題を大幅に回避できます。要約すると次のようになります。
1) in と not in は注意して使用してください。in の代わりに between を使用し、not in の代わりに not exists を使用するようにしてください。 5. クエリキャッシュを使用する 多数の同一クエリが複数回実行されると、クエリ結果はキャッシュに格納されるため、後続の同一クエリは操作なしでキャッシュされた結果に直接アクセスできます。 MySQL クエリ キャッシュには、クエリによって返された完全な結果が保存されます。クエリがキャッシュにヒットすると、MySQL は解析、最適化、実行の切り捨てをスキップして結果を返します。 これはクエリ パフォーマンスを向上させる最も効果的な方法の 1 つであり、MySQL エンジンによって処理されます。通常、MySQL はデフォルトでクエリ キャッシュを有効にしないため、手動で有効にする必要があります。 クエリ キャッシュはアプリケーションに対して完全に透過的です。アプリケーションは、MySQL がクエリを通じて結果を返すのか、実際の実行を通じて結果を返すのかを気にする必要はありません。実際、これら 2 つの方法の結果はまったく同じです。つまり、キャッシュをクエリするために必要な構文はありません。 現在の汎用サーバーがより強力になるにつれて、クエリ キャッシュがサーバーのスケーラビリティに影響を与える要因であることがわかります。サーバー全体のリソース競合の単一ポイントになる可能性があり、マルチコア サーバーでサーバーのデッドロックを引き起こす可能性もあります。したがって、ほとんどの場合、クエリ キャッシュはデフォルトでオフにする必要があります。クエリ キャッシュが非常に便利な場合は、数十メガバイトの小さなキャッシュ スペースを構成できます。 (選択する際にはトレードオフが必要です) クエリ キャッシュ構成には次のパラメータを使用できます。
クエリ キャッシュを有効にするかどうか。 OFF、ON、または DEMAND に設定できます。DEMAND は、クエリ ステートメントで sql_cache に明示的に書き込まれたステートメントのみがクエリ キャッシュに格納されることを意味します。
クエリ キャッシュで使用される合計メモリ領域 (バイト単位)。この値は 1024 の整数倍である必要があります。そうでない場合、実際に割り当てられたデータは指定されたサイズと異なります。
クエリ キャッシュに割り当てられるメモリの最小単位。
キャッシュするクエリ結果の最大数。クエリ結果がこの値より大きい場合、キャッシュされません。クエリ キャッシュはデータが生成されるとすぐにキャッシュを試行するため、すべての結果が返されるまで、MySQL はクエリ結果が制限を超えているかどうかを認識しません。 クエリキャッシュに関しては、次の章で個別に詳しく説明します。 上記はMySQL最適化SQL文テクニックの詳細です。MySQL最適化SQL文の詳細については、123WORDPRESS.COMの他の関連記事に注目してください。 以下もご興味があるかもしれません:
|
<<: WeChatアプレットbindtapとcatchtapの違いの詳細な説明
>>: Docker コンテナ アプリケーションで避けるべき 10 の悪い習慣
jsvc の紹介実稼働環境では、Tomcat はデーモン モードで実行する必要があります。Tomc...
背景検索エンジンで「.htaccess キャッシュ」というキーワードを検索すると、ウェブサイトのファ...
結果:実装コード: html <!-- よろしければハートを付けてください! --> &...
<br />私はいつもYahooのウェブデザインが素晴らしいと信じてきました。しかし、こ...
序文会社の業務上のニーズにより、独自の MongoDB サービスを構築する予定です。MongoDB ...
目次DockerコンテナのエクスポートDockerコンテナのインポートこの記事では主に、コンテナ...
1. psshを確認してインストールします。yum list pssh 2. キーレスログインが設定...
この記事では、JavaScriptでカルーセルを実装するための具体的なコードを参考までに紹介します。...
Navicat で MySql スケジュールタスクを作成する詳細な説明イベントは、MySQL が特定...
私は最近、YouTube の CSS アニメーション効果チュートリアル シリーズをフォローしています...
1.1 iptablesファイアウォールの概要Netfilter/Iptables (以下、Ipta...
Linux マスターになりたいなら、いくつかの Linux コマンドを習得することが不可欠です。 L...
序文前回の記事では Hadoop をインストールしましたが、今回は Hbase をインストールします...
序文現在の JavaScript には列挙の概念がありません。一部のシナリオでは、列挙を使用するとデ...
閉鎖サービス nginx 停止systemctl 停止 nginx起動するサービス nginx 開始...