記事ディレクトリ
記事の文字数は約12,700文字、読了時間は約42分、ブックマークしてゆっくり読むのがおすすめ!! !
1.索引
-
インデックスを使用する理由
- 一意のインデックスを作成することにより、データベース テーブル内のデータの各行の一意性を保証できます。
- インデックスを作成する主な理由であるデータの取得を大幅に高速化できます。
- サーバーがソートと一時テーブルを回避するのに役立ちます。
- ランダム IO をシーケンシャル IO に変えます。
- 特にデータの参照整合性を実現する際に、テーブル間の接続を高速化できます。
-
インデックスの分類
- 通常のインデックス: クエリのみを高速化します
- 一意のインデックス: 高速化されたクエリ + 一意の列の値 (null を持つことができます)
- 主キー インデックス: 高速化されたクエリ + 一意の列値 (null は不可) + テーブル内の 1 つのみ
- 複合インデックス: 複数の列の値がインデックスを形成します。これは、組み合わせ検索に特に使用され、その効率はインデックスのマージよりも優れています
- 全文索引: テキストの内容を分割して検索
- Index Merge : 複数の単一列インデックスを使用して検索を結合します
- Covering index : 選択したデータ列は、データ行を読み取らずにインデックスからのみ取得できます. つまり、クエリ列は構築されたインデックスによってカバーされている必要があります.
- クラスター化インデックス: テーブル データは主キーと共に格納され、主キー インデックスのリーフ ノードには行データ (主キー値を含む) が格納され、セカンダリ インデックスのリーフ ノードには行の主キー値が格納されます。B+ ツリーはインデックスの格納構造として使用され、非リーフ ノードはすべてインデックス キーワードですが、非リーフ ノードのキーワードは、対応するレコードの特定のコンテンツまたはコンテンツ アドレスを格納しません。葉ノードのデータが主キーで特定のレコード(データ内容)
-
インデックスを作成する必要がある/作成しない場合
インデックスの最大の利点はクエリ速度の向上ですが、インデックスには次のような欠点もあります。
- 物理的なスペースを占有する必要があり、数字が大きいほど占有スペースが大きくなります。
- インデックスの作成と維持には時間がかかります。この時間は、データの量が増えるにつれて長くなります。
- テーブルの追加、削除、および変更の効率が低下します。インデックスが追加、削除、および変更されるたびに、インデックスの順序を維持するために B+ ツリーを動的に維持する必要があります。
そのため、インデックスはマスターキーではなく、シーンに合わせて使い分けることも。
いつインデックスを使用する必要がありますか?
- 商品コードなどの固有の制限のあるフィールド。
WHERE
クエリ条件によく使用されるフィールドは、テーブル全体のクエリ速度を向上させることができます. クエリ条件がフィールドでない場合, 結合インデックスを確立できます.- B+Tree のレコードはすべて、インデックスが作成された後にソートされることがわかっているため、クエリを実行するときに再度ソートする必要がないように、およびフィールドによく使用されます
GROUP BY
。ORDER BY
インデックスを作成する必要がないのはいつですか?
WHERE
条件で使用されていないフィールドの場合、インデックスの値はクイック ポジショニングです。インデックスが物理スペースを占有するため、通常、インデックスを作成する必要がないフィールドを見つけることができない場合GROUP BY
。ORDER BY
- フィールドには重複データが多く、インデックスを作成する必要はありません.たとえば、性別フィールドには男性と女性しかありません.データベーステーブルに男性と女性のレコードが均等に分散されている場合の場合、どの値を検索しても半分のデータしか得られないことがあります。In these cases, it is better not to index, because MySQL has a query optimizer. クエリ オプティマイザーは、特定の値がテーブル内のデータ行の高い割合で表示されることを検出すると、通常、インデックスを無視して完全なテーブルを実行します。スキャンです。
- テーブル データが少なすぎる場合、インデックスを作成する必要はありません。
- 頻繁に更新されるフィールドは、インデックスを作成する必要はありません。インデックス フィールドは頻繁に変更され、B+Tree の順序を維持する必要があるため、インデックスを頻繁に再構築する必要があり、データベースのパフォーマンスに影響します。
-
インデックスを最適化する方法
-
プレフィックス インデックスの最適化。
プレフィックス インデックスは、名前が示すように、フィールド内の文字列の最初の数文字を使用してインデックスを構築することです。
プレフィックス インデックスは、インデックス フィールドのサイズを縮小するために使用されます。これにより、インデックス ページに格納されるインデックス値が増加し、インデックスのクエリ速度が効果的に向上します。一部の大きな文字列フィールドがインデックスとして使用される場合、プレフィックス インデックスを使用すると、インデックス アイテムのサイズを小さくするのに役立ちます。
-
インデックスの最適化をカバー。
カバリング インデックスは、SQL のクエリのすべてのフィールドを参照します。これらのインデックスは、インデックス B+Tree のリーフ ノードで見つけることができ、レコードはセカンダリ インデックスからクエリされ、クラスター化されたインデックスを通じて取得する必要はありません。テーブルに戻る操作を回避できるインデックス クエリ。
カバリング インデックスを使用する利点は、レコードの行全体を含むすべての情報をクエリする必要がないことです。これにより、多くの I/O 操作が削減されます。
-
主キー インデックスは、自己インクリメント式であることが望ましいです。
自動インクリメント主キーを使用すると、挿入された新しいデータはそれぞれ現在のインデックス ノードの位置に順番に追加され、既存のデータを移動する必要はありません. ページがいっぱいになると、新しいページが表示されます自動的に開かれます。新しいレコードが挿入されるたびに追加操作が行われ、データを再移動する必要がないため、このデータ挿入方法は非常に効率的です。
主キー フィールドの長さが短すぎると、セカンダリ インデックスのリーフ ノードが小さくなるため (セカンダリ インデックスのリーフ ノードに格納されたデータがプライマリ キーになるため)、プライマリ キー フィールドの長さはあまり大きくしないでください。したがって、セカンダリ インデックスが占めるスペースも小さくなります。
-
インデックスの失敗を防ぎます。
インデックスを使用しても、クエリ時にインデックスが使用されるわけではないため、インデックスが失敗するクエリステートメントを記述しないように、どのような状況でインデックスが失敗するかを頭の中で知っておく必要があります。低い。
インデックス障害の場合:
- 左または左ファジー マッチングを使用すると、
like %xx
つまりlike %xx%
これら 2 つの方法でインデックスが失敗します。 - クエリ条件でインデックス列に対して計算、関数、および型変換操作を実行すると、これらのケースによってインデックス エラーが発生します。
- 結合インデックスを正しく使用するには、左端の一致の原則に従う必要があります。つまり、左端の最初の方法に従ってインデックスを一致させる必要があります。そうしないと、インデックスが無効になります。
- WHERE 句で、OR の前の条件付き列がインデックス付きの列であるが、OR の後の条件付きの列がインデックス付きの列でない場合、インデックスは失敗します。
- 左または左ファジー マッチングを使用すると、
-
-
索引を使用する際の注意事項
通常、MySQL インデックスは、WHERE 条件でデータ行を照合する際の検索速度を向上させるために使用されます. インデックスの使用方法の詳細と注意事項があります.
関数、演算、否定演算子、結合条件、複数の単一列インデックス、左端の接頭辞の原則、範囲クエリ、NULL 値を持つ列を含まない、ステートメントが列に対して関数と演算を使用しないなど
- 1) 列で関数を使用しないでください。これにより、インデックスが失敗し、完全なテーブル スキャンが実行されます。
- 2) or で != or not などの否定演算子を使用しないようにしてください。
- 3) 複数の単一列インデックスは最適な選択ではありません
- 4) 複合指数の左端接頭原則
- 5) インデックスをカバーする利点
- 6) 複数列クエリに対する範囲クエリの影響
- 7) インデックスには NULL 値を持つ列は含まれません
- 8) 暗黙の変換の影響
- 9) like 文のインデックス無効化問題
-
インデックスが B+ ツリーをインデックスとして使用する理由
主な理由: B+ ツリーは、リーフ ノードがトラバースされ、データベース内の範囲ベースのクエリが非常に頻繁に行われる限り、ツリー全体のトラバースを実現できますが、B ツリーはすべてのノードを中間の順序でしかトラバースできません。非効率すぎる。
B+tree のディスク読み取りおよび書き込みコストは低く、B+tree のクエリ効率はより安定しています. 範囲ベースのクエリは非常に頻繁であり、B-tree はすべてのノードを順番にしか走査できないため、非効率的です.
B+ツリーの特徴
- すべてのキーワードはリーフ ノードのリンク リスト (密なインデックス) に表示され、リンク リスト内のキーワードはたまたま順番に並んでいます。
- 葉以外のノードにヒットすることはできません。
- 非リーフ ノードはリーフ ノードのインデックス(スパース インデックス)に相当し、リーフ ノードは(キーワード)データを格納するデータ層に相当します。
-
インデックス エラーとは何ですか?
- 左または左ファジー マッチングを使用すると、
like %xx
つまりlike %xx%
これら 2 つの方法でインデックスが失敗します。 - クエリ条件でインデックス列に関数を使用すると、インデックスが失敗します。
- クエリ条件でインデックス列に対して式計算を実行する場合、インデックスを使用できません。
- MySQL は文字列と数値の比較を検出すると、自動的に文字列を数値に変換してから比較します。If string is a index column and the input parameter in the conditional statement is a number, then the index column will take implicit type conversion. 暗黙的な型変換は CAST 関数によって実装されるため、インデックス列に含まれているため、インデックスが失敗する原因となります。
- 結合インデックスを正しく使用するには、左端の一致の原則に従う必要があります。つまり、左端の最初の方法に従ってインデックスを一致させる必要があります。そうしないと、インデックスが無効になります。
- WHERE 句で、OR の前の条件付き列がインデックス付きの列であるが、OR の後の条件付きの列がインデックス付きの列でない場合、インデックスは失敗します。
- 左または左ファジー マッチングを使用すると、
-
Bツリーインデックスの実装におけるMyISAMとInnoDBの違いは何ですか?
-
MyISAM では B+Tree リーフノードのデータフィールドにデータレコードのアドレスが格納されている. インデックスを検索するときは, まず B+Tree 検索アルゴリズムに従ってインデックスを検索し, 指定したキーが存在する場合はその値を取り出す.データ フィールドの値は、「非クラスター化インデックス」と呼ばれる、対応するデータ レコードを読み取るためのアドレスです。
-
InnoDBはデータファイル自体がインデックスファイルである.MyISAMと比較してインデックスファイルとデータファイルが分離されており,テーブルデータファイル自体がB+Treeで構成されたインデックス構造である.ツリーのノードデータ領域は完全なデータを保存する. records. 、このインデックスのキーはデータ テーブルのプライマリ キーであるため、InnoDB テーブル データ ファイル自体がプライマリ インデックスであり、これは「クラスター化インデックス」またはクラスター化インデックスと呼ばれ、残りのインデックスは補助として使用されます。インデックス、および補助インデックスのデータ フィールドには、対応するレコード アドレスの代わりに主キーの値が格納されます。これも MyISAM とは異なります。
プライマリ インデックスに基づいて検索する場合は、キーが配置されているノードを直接見つけてデータを取得できますが、補助インデックスに基づいて検索する場合は、最初にプライマリ キーの値を取得してから、プライマリ キーを通過する必要があります。再びインデックス。したがって、テーブルを設計するときは、長すぎるフィールドを主キーとして使用することはお勧めできません。また、単調でないフィールドを主キーとして使用することもお勧めしません。これにより、主インデックスが頻繁に分割されます。
-
2.事務
-
ビジネスの4つの特徴
- 原子性: トランザクションは実行の最小単位であり、分割することはできません。トランザクションの原子性により、アクションが完全に完了するか、まったく影響を与えないことが保証されます。
- 一貫性: トランザクションが実行される前後に、データベースはある一貫した状態から別の一貫した状態に遷移します。
- 分離: データベースに同時にアクセスする場合、ユーザーの業務は他のトランザクションによって干渉されず、同時トランザクション間のデータベースは独立しています。
- 持続性: トランザクションがコミットされた後。データベース内のデータに対する変更は永続的であり、データベースに障害が発生しても、データベースに影響を与えることはありません。
-
トランザクションのダーティー読み取り、反復不能読み取り、ファントム読み取り
ダーティーリード: トランザクションが別の「コミットされていないトランザクションによって変更されたデータ」を「読み取る」場合、「ダーティーリード」現象が発生したことを意味します。
幻読:クエリ条件を満たす「レコード数」を1回のトランザクションで複数回問い合わせる 前後の2回の問い合わせレコード数が異なる場合、「幻読」現象が発生していることを意味します。
変更の破棄: 2 つの書き込みトランザクション T1 と T2 が同時に A=0 をインクリメントし、結果 T2 が T1 を上書きし、最終結果が 2 ではなく 1 になり、トランザクションが上書きされます。
Non-repeatable read : トランザクション内で同じデータが複数回読み出され、前後の 2 回読み込んだデータが異なる場合、「non-repeatable read」という現象が発生したことを意味します。
-
トランザクション分離レベルとは何ですか?
- READ_UNCOMMITTED (コミットされていない読み取り): コミットされていないデータ変更の読み取りを許可する最低の分離レベル。これにより、ダーティ リード、ファントム リード、または反復不可能な読み取りが発生する可能性があります。
- READ_COMMITTED (コミットされた読み取り): 並行トランザクションによってコミットされたデータを読み取ることができます。これにより、ダーティ リードを防ぐことができますが、ファントム リードまたは反復不可能な読み取りが引き続き発生する可能性があります。
- REPEATABLE_READ (反復可能な読み取り): データが独自のトランザクション自体によって変更されない限り、同じフィールドの複数の読み取りの結果は一貫しています。
- SERIALIZABLE (シリアル化): 最高の分離レベルで、ACID 分離レベルに完全に準拠しています。すべてのトランザクションは 1 つずつ実行されるため、トランザクション間の干渉の可能性はありません。つまり、このレベルにより、ダーティ リード、反復不能リード、ファントム リードを防ぐことができます。しかし、これはプログラムのパフォーマンスに深刻な影響を与えます。通常、このレベルも使用されません。
分離レベル ダーティリード 繰り返し不可能な読み取り ファントムリード READ-UNCOMMITTED コミットされていない読み取り √ √ √ READ-COMMITTED 読み取りコミット × √ √ REPEATABLE-READ 繰り返し読み取り × × √ SERIALIZABLE シリアライズ可能な読み取り × × × MySQL InnoDB ストレージ エンジンでサポートされているデフォルトの分離レベルはREPEATABLE-READ (再読み取り可能)です。
ここで、SQL 標準との違いは、InnoDB ストレージ エンジンがREPEATABLE-READ (再読み取り可能) トランザクション分離レベルでNext-Key Lock ロックアルゴリズムを使用するため、他の SQL とは異なるファントム読み取りを回避できることです。 SQL Server などのシステムは異なります。したがって、InnoDB ストレージ エンジンでサポートされるデフォルトの分離レベルは REPEATABLE-READ (再読み取り可能) であり、トランザクションの分離要件を完全に保証できます。つまり、SQL 標準の SERIALIZABLE (シリアル化可能) 分離レベルに達しています。
-
読み取りビューの役割
読み取りビューには 4 つの重要なフィールドがあります。
- m_ids: 読み取りビューが作成されたときに、現在のデータベース内の「アクティブなトランザクション」のトランザクション ID のリストを参照します。これはリストであることに注意してください。「アクティブなトランザクション」とは、開始されたがまだコミットされていないトランザクションを指します。
- min_trx_id : 読み取りビューが作成された時点で、現在のデータベース内の「アクティブなトランザクション」の中で最小のトランザクション ID、つまり m_ids の最小値を持つトランザクションを指します。
- max_trx_id: これは m_ids の最大値ではありませんが、Read View を作成するときに現在のデータベースの次のトランザクションに与えられるべき id 値です。つまり、グローバル トランザクション内の最大のトランザクション id 値 + 1 です。
- Creator_trx_id: Read View を作成したトランザクションのトランザクション IDを参照します。
InnoDB ストレージ エンジンを使用するデータベース テーブルの場合、そのクラスター化されたインデックス レコードには、次の 2 つの非表示の列が含まれます。
- trx_id: トランザクションがクラスター化インデックス レコードを変更すると、トランザクションのトランザクション ID が trx_id 非表示の列に記録されます。
- roll_pointer を使用すると、クラスター化されたインデックス レコードが変更されるたびに、古いバージョンのレコードが元に戻すログに書き込まれ、この非表示の列は各古いバージョンのレコードへのポインターになるため、それを使用してレコードを見つけることができます。
「バージョン チェーン」を介して同じレコードにアクセスする同時トランザクションの動作を制御することを、MVCC (マルチバージョン同時実行制御) と呼びます。
-
MySQL の反復可能な読み取りレベルは、ファントム読み取りを完全に解決しますか?
- スナップショット読み取り(通常の select ステートメント)の場合、ファントム読み取りは MVCC によって解決されます。反復可能な読み取り分離レベルでは、トランザクションの実行中に表示されるデータは、データの一部が挿入された場合でも、トランザクションの開始時に表示されるデータと常に一致するためです。途中で他のトランザクションによって処理されますが、このデータはクエリできないため、ファントム読み取りの問題を回避するのに非常に適しています。
- 現在の読み取り(select ... for update およびその他のステートメント)では、次のキー ロック (レコード ロック + ギャップ ロック) を使用してファントム read が解決されます。 next-key ロックが追加されます. next-key ロックの範囲内で別のトランザクションがレコードを挿入すると、insert ステートメントがブロックされ、正常に挿入できないため、幻読の問題を回避するのに非常に役立ちます。
「read commit」および「repeatable read」分離レベルのトランザクションの場合、これらは Read View を通じて実装され、それらの違いは Read View を作成するタイミングにあります。
- 「読み取りコミット」分離レベルは、選択ごとに新しい読み取りビューを生成することです。これは、トランザクション中に同じデータが複数回読み取られ、前後に 2 回読み取られたデータが矛盾する可能性があることを意味します。トランザクションはレコードを変更し、トランザクションをコミットします。
- 「反復可能読み取り」分離レベルは、トランザクションの開始時に読み取りビューを生成し、トランザクション全体でこの読み取りビューを使用して、トランザクション中に読み取られるデータがすべてトランザクション開始前のレコードであることを保証することです。
これら 2 つの分離レベルの実装は、「トランザクションの読み取りビュー内のフィールド」と「レコード内の 2 つの非表示の列」の比較を通じて、同じレコードにアクセスする同時トランザクションの動作を制御することです。これは MVCC (マルチバージョン同時実行制御)。
ファントム リーディング シナリオの 2 つの例。
最初の例: スナップショット読み取りの場合、MVCC はファントム読み取りを完全に回避することはできません。トランザクション A がトランザクション B によって挿入されたレコードを更新すると、トランザクション A の前後の 2 つのクエリのレコード エントリが異なるため、ファントム読み取りが発生します。
2 番目の例: 現在の読み取りの場合、トランザクションの開始後に現在の読み取りが実行されていないが、スナップショットの読み取りが最初に実行され、次にこの期間中に別のトランザクションがレコードを挿入した場合、トランザクションが現在の読み取りを使用するとき2 つのクエリのレコード エントリが異なることが判明したため、幻読が発生します。
したがって、MySQL 反復可能読み取り分離レベルは、幻聴を完全に解決するわけではありませんが、幻聴の発生を大幅に回避します。
-
MySQL にトランザクション ロールバック メカニズムがあるのはなぜですか
MySQL では、回復メカニズムはロールバック ログ (元に戻すログ) によって実装されます. トランザクションによって行われたすべての変更は、最初にロールバック ログに記録され、次にデータベース内の対応する行が書き込まれます. トランザクションがコミットされると、再度ロールバックすることはできません。
ロールバック ログの機能: 1) エラーが発生したとき、またはユーザーが ROLLBACK を実行したときに、ロールバック関連の情報を提供できます。 2) システム全体がクラッシュし、データベース プロセスが直接強制終了された後、ユーザーがデータベース プロセスを再度開始したときに、ロールバックに関連する情報を提供できます。ロールバック ログをクエリして、以前の未完了のトランザクションをロールバックします。これには、データの前にロールバック ログをディスクに永続化する必要があります。これが、最初にログを書き込んでからデータベースを書き込む必要がある主な理由です。
3. ストレージエンジン
-
InnoDB の紹介
InnoDB はトランザクション データベースの優先エンジンであり、トランザクション セキュリティ テーブル (ACID) をサポートし、行ロックと外部キーをサポートします。InnoDB はデフォルトの MySQL エンジンです。
InnoDB の主な機能は次のとおりです。
-
InnoDB は、コミット、ロールバック、およびクラッシュ リカバリ機能を備えたトランザクション セーフ (ACID 準拠) ストレージ エンジンを MySQL に提供します。
InnoDB は行レベルでロックし、SELECT ステートメントで Oracle のような非ロック読み取りも提供します。これらの機能により、マルチユーザー展開とパフォーマンスが向上します。SQL クエリでは、同じクエリ内であっても InnoDB テーブルを他の MySQL テーブル タイプと自由に混在させることができます。
-
InnoDB は、膨大な量のデータを処理する際に最大のパフォーマンスを発揮するように設計されています。その CPU 効率は、おそらく他のディスクベースのリレーショナル データベース エンジン ロックとは比べものになりません。
-
InnoDB ストレージ エンジンは、MySQL サーバーと完全に統合されています. InnoDB ストレージ エンジンは、メイン メモリにデータとインデックスをキャッシュするための独自のバッファ プールを維持します. InnoDB は、そのテーブルとインデックスを論理テーブルスペースに編成します。論理テーブルスペースには、複数のファイル (または raw ディスク ファイル) を含めることができます。これは、たとえば、各テーブルが個別のファイルに格納されている MyISAM テーブルとは異なります。InnoDB テーブルは、ファイル サイズが 2GB に制限されているオペレーティング システムであっても、任意のサイズにすることができます。
-
InnoDB は外部キー整合性制約をサポートしています.テーブルにデータを格納する場合、各テーブルのストレージは主キーの順序で格納されます.テーブルの定義時に主キーが指定されていない場合、InnoDB は 6 バイトの ROWID を生成しますこれを主キーとして使用します。
-
InnoDB は、高いパフォーマンスを必要とする多くの大規模なデータベース サイトで使用されています。InnoDB はディレクトリを作成しません. InnoDB を使用する場合、MySQL は ibdata1 という名前の 10MB の自動拡張データ ファイルと、MySQL データ ディレクトリの下に ib_logfile0 および ib_logfile1 という名前の 2 つの 5MB のログ ファイルを作成します。
-
-
MyISAM の紹介
MyISAM は ISAM ストレージ エンジンに基づいており、それを拡張しています。これは、Web、データ ウェアハウジング、およびその他のアプリケーション環境で最も一般的に使用されるストレージ エンジンの 1 つです。MyISAM は挿入とクエリの速度が高いですが、トランザクションをサポートしていません。
MyISAM の主な機能は次のとおりです。
- 大きなファイル (最大 63 ビットのファイル長) は、大きなファイルをサポートするファイル システムおよびオペレーティング システムでサポートされます。
- 動的にサイズ変更された行は、削除操作と更新操作および挿入操作が混在している場合、断片化が少なくなります。これは、隣接する削除されたブロックをマージし、次のブロックが削除された場合に次のブロックに拡張することによって自動的に行われます。
- MyISAM テーブルごとのインデックスの最大数は 64 で、再コンパイルすることで変更できます。インデックスあたりの列の最大数は 16 です。
- キーの最大長は 1000 バイトです. これはコンパイルによって変更することもできます. キーの長さが 250 バイトを超える場合, 1024 バイトを超えるキーが使用されます.
- BLOB および TEXT 列には索引を付けることができます。
- インデックス付きの列では NULL を使用できます。この値はキーごとに 0 ~ 1 バイトを占めます。
- すべての数値キーは、より高いインデックス圧縮を可能にするために、最初に大きなバイトが格納されます。
- 各 MyISAM タイプ テーブルには AUTO_INCREMENT の内部列があり、これは INSERT および UPDATE が操作されると更新され、AUTO_INCREMENT 列は同時に更新されます。したがって、MyISAM 型テーブルの AUTO_INCREMENT 列の更新は、InnoDB 型の AUTO_INCREMENT 型よりも高速です。
- データ ファイルとインデックス ファイルは、別のディレクトリに配置できます。
- 各文字列は、異なる文字セットを持つことができます。
- VARCHAR を持つテーブルは、固定または動的レコード長を持つことができます。
- VARCHAR および CHAR カラムは 64KB まで大きくすることができます。
-
MEMORYの紹介
MEMORY ストレージ エンジンは、テーブルのデータをメモリに格納し、他のテーブル データのクエリや参照を行わずに高速アクセスを提供します。
MEMORY の主な機能は次のとおりです。
- MEMORY テーブルには、テーブルごとに最大 32 個のインデックス、インデックスごとに 16 列、および最大キー長 500 バイトを含めることができます。
- MEMORY ストレージ エンジンは、HASH および BTREE ミニチュアを実行します。
- MEMORY テーブルに一意でないキー値を含めることができます。
- MEMORY テーブルは、固定レコード長形式を使用します。
- MEMORY は、BLOB または TEXT 列をサポートしていません。
- MEMORY は、NULL 値を含むことができる列の AUTO_INCREMENT 列とインデックスをサポートします。
- MEMORY テーブルはすべてのクライアント間で共有されます (他の非 TEMPORARY テーブルと同様)。
- MEMORY テーブルのメモリはメモリに格納され、メモリは MEMORY テーブルと、クエリ処理中にサーバーによって作成される内部テーブルの間で共有されます。
- MEMORY テーブルの内容が不要になったときに MEMORY テーブルで使用されているメモリを解放するには、DELETE FROM または TRUNCATE TABLE を実行するか、テーブル全体を削除する必要があります (DROP TABLE を使用)。
-
アーカイブ紹介
アーカイブ ストレージ エンジンのアプリケーション シナリオは、その名前の縮図であり、主にアーカイブに使用されます。アーカイブ ストレージ エンジンは、select と insert のみをサポートします. 最も優れた機能は、高速な挿入、高速なクエリ、および小さなフットプリントです。
ファイル システム ストレージの機能
- zlib を使用してテーブル データを圧縮し、ディスク I/O を減らします (いくつかの Tinnodb テーブルは、アーカイブに数百メガバイトしか必要としません)
- データは .ARZ サフィックスが付いたファイルに保存されます
- .frm ファイル
特徴
- 挿入、置換、および選択のみがサポートされています
- 行レベルのロックと専用バッファをサポートして高い同時実行性を実現
- インデックスは自己インクリメント ID 列でのみ許可されます
- パーティショニングはサポートされていますが、トランザクション処理はサポートされていません
-
データベースエンジン InnoDB と MyISAM の違い
InnoDB
- これは MySQL のデフォルトのトランザクション ストレージ エンジンです. サポートされていない機能が必要な場合にのみ、他のストレージ エンジンの使用を検討してください.
- 4 つの標準分離レベルが実装されています。デフォルト レベルは反復可能な読み取り (REPEATABLE READ) です。反復可能読み取り分離レベルでは、マルチバージョン同時実行制御 (MVCC) + ギャップ ロック (Next-Key Locking) によってファントム読み取りが防止されます。
- メイン インデックスはクラスター化されたインデックスであり、データをインデックスに保存してディスクを直接読み取らないようにするため、クエリのパフォーマンスが大幅に向上します。
- ディスクからデータを読み取るときの予測読み取り、読み取り操作を高速化して自動的に作成できるアダプティブ ハッシュ インデックス、挿入操作を高速化できる挿入バッファーなど、多くの最適化が内部で行われています。
- 実際のオンライン ホット バックアップをサポートします。他のストレージ エンジンはオンライン ホット バックアップをサポートしていません. 一貫性のあるビューを取得するには、すべてのテーブルへの書き込みを停止する必要があります. 読み取りと書き込みが混在するシナリオでは、書き込みの停止は読み取りの停止を意味する場合もあります.
MyISAM
- デザインはシンプルで、データはコンパクトな形式で保存されます。読み取り専用データ、または修復操作を許容できるほどテーブルが小さい場合は、引き続き使用できます。
- 圧縮テーブル、空間データ インデックスなど、多数の機能を提供します。
- トランザクションはサポートされていません。
- 行レベルのロックはサポートされておらず、テーブル全体をロックすることしかできません. 読み取り時には、読み取りが必要なすべてのテーブルに共有ロックを追加し、書き込み時にはテーブルに排他ロックを追加します. ただし、テーブルに読み取り操作がある間、新しいレコードをテーブルに挿入することもできます。これは同時挿入 (CONCURRENT INSERT) と呼ばれます。
要約する
- トランザクション: InnoDB はトランザクション対応で
Commit
、Rollback
ステートメントを使用できます。 - 同時実行性: MyISAM はテーブル レベルのロックのみをサポートしますが、InnoDB は行レベルのロックもサポートします。
- 外部キー: InnoDB は外部キーをサポートしています。
- バックアップ: InnoDB はオンライン ホット バックアップをサポートしています。
- クラッシュ回復: MyISAM は InnoDB よりもクラッシュ後に破損する可能性がはるかに高く、回復は遅くなります。
- その他の機能: MyISAM は、圧縮されたテーブルと空間データ インデックスをサポートしています。
該当するシナリオ: MyISAM は次の場合に適しています: 挿入が頻繁に行われず、クエリが非常に頻繁に行われる. 多数の SELECT が実行される場合、MyISAM はトランザクションなしでより適切な選択です. InnoDB は次のような場合に適しています: 信頼性要件が比較的高い、またはトランザクションが必要な場合、テーブルの更新とクエリが頻繁に行われる場合、多数の INSERT または UPDATE がある場合
4. ロック機構
-
MySQL にはどのようなロックがありますか (グローバル ロック/テーブル レベル ロック/行レベル ロック)
グローバルロック
MyISAM はテーブル ロックのみをサポートし、InnoDB はテーブル ロックと行ロックをサポートし、デフォルトは行ロックです。
テーブル レベルのロック: 低オーバーヘッド、高速ロック、デッドロックなし。ロックの粒度は大きく、ロックの競合の可能性は最も高く、並行性の量は最も低くなります。
- テーブル ロック: テーブル レベルのロック
- メタデータ ロック: MDL の正式名称はメタデータ ロック、つまりメタデータ ロックであり、一般に辞書ロックとも呼ばれます。MDL の主な役割は、データベース オブジェクトへの同時アクセスを管理し、メタデータの一貫性を確保することです。
- インテント ロック: インテンション ロックは、下位レベルのリソースの共有ロックまたは排他ロックを保護するために、リソース階層の 1 つのレベルに配置されるロックです。
- AUTO-INC ロック: AUTO-INC ロックは特別なテーブル ロック メカニズムです. 別のトランザクションがコミットされた後、ロックは解放されませんが、insert ステートメントが実行されるとすぐに解放されます。
行レベルのロック: 高いオーバーヘッド、遅いロック、およびデッドロック。ロックの粒度は小さく、ロックの競合の可能性は小さく、同時実行性は最高です。
- レコード ロック: 単一行レコードに対するロック。
- ギャップ ロック: ギャップ ロック、レコード自体を除く範囲をロックします。
- 次のキー ロック: レコード + ギャップは、レコード自体を含む範囲をロックします。
- 挿入意図ロック: 挿入意図ロックの名前に意図ロックがありますが、これは意図ロックではなく、行レベル ロックに属する特殊なギャップ ロックです。
-
MySQL のロック方法
MySQL 行レベル ロックのロック規則。
一意のインデックスに相当するクエリ:
- 照会されたレコードが「存在する」場合、インデックス ツリーでこのレコードを見つけた後、レコードのインデックスの次のキー ロックは「レコード ロック」に縮退します。
- クエリ レコードが「存在しない」場合、インデックス ツリーがクエリ レコードより大きい最初のレコードを見つけた後、レコードのインデックスの次のキー ロックは「ギャップ ロック」に縮退します。
一意でないインデックスに相当するクエリ:
- クエリされたレコードが「存在する」場合、それは一意のインデックスではないため、同じインデックス値を持つレコードが存在する必要があるため、非一意のインデックスに相当するクエリ プロセスは、最初の非修飾セカンダリがスキャンされるまでスキャン プロセスです。インデックス レコードスキャンを停止し、スキャン プロセス中に次のキー ロックがスキャンされた副次インデックス レコードに追加され、条件を満たさない最初の副次インデックス レコードに対して、副次インデックスの次のキー ロック キー ロックが縮退します。ギャップロックに。同時に、クエリ条件を満たすレコードの主キー インデックスにレコード ロックが追加されます。
- 照会されたレコードが「存在しない」場合、最初の修飾されていない副次索引レコードがスキャンされ、副次索引の次のキー・ロックがギャップ・ロックに縮退します。クエリ条件を満たすレコードがないため、主キー インデックスはロックされません。
非一意インデックスと主キー インデックスの範囲クエリのロック規則は、次の点で異なります。
- ユニークインデックスが一定の条件を満たすと、インデックスのネクストキーロックがギャップロックまたはレコードロックに縮退します。
- 一意でないインデックス範囲クエリの場合、インデックスの次のキー ロックは、ギャップ ロックとレコード ロックに縮退しません。
-
幻読問題を解決するMySQLのレコードロック+ギャップロック
MySQL の反復可能読み取り分離レベルでは、レコード ロック + ギャップ ロックが現在の読み取りステートメントのインデックスに追加されます。これにより、追加、削除、および変更時に他のトランザクションによって引き起こされるファントム読み取りの問題を回避できます。
注意すべきことの 1 つは、update、delete、select ... for update およびその他のロック プロパティを持つステートメントを実行する場合、ステートメントがインデックスを使用しているかどうかを確認する必要があることです。ロックはテーブル全体をロックすることと同じであり、これは深刻な問題です。
-
デッドロックに必要な4つの条件
-
相互に排他的な条件: リソースは、一度に 1 つのプロセスでしか使用できません。
-
要求と保持の条件: リソースを要求したためにプロセスがブロックされた場合、プロセスは取得したリソースを保持します。
-
非剥奪条件: プロセスによって取得されたリソースは、使い果たされる前に強制的に剥奪することはできません。
-
循環待機状態: 多数のプロセスが頭と尾の循環待機リソース関係を形成します。
-
-
MySQL デッドロックの問題を解決する方法
デッドロックとは、2 つ以上のトランザクションが同じリソースを占有し、互いのリソースをロックするように要求するという悪循環に陥る現象です。
デッドロックを解決する一般的な方法
- 異なるプログラムが複数のテーブルに同時にアクセスする場合は、同じ順序で。これにより、デッドロックの可能性を大幅に減らすことができます。
- 同じトランザクションで、必要なすべてのリソースを一度に、デッドロックの可能性を減らします。
- デッドロックが発生しやすいビジネス パーツの場合は、アップグレードテーブルレベルのロックによってデッドロックの可能性を減らすことができます。
-
データベースの悲観的ロックと楽観的ロックの原則と適用シナリオ
悲観的ロックは、最初にロックを取得してからビジネス操作を実行します。通常、SELECT ... FOR UPDATE などのステートメントを使用してデータをロックし、他のトランザクションが誤ってデータを変更するのを防ぎます。データベースが SELECT ... FOR UPDATE を実行すると、select 内のデータ行の行ロックが取得され、select for update によって取得された行ロックは、現在のトランザクションの終了時に自動的に解放されます。トランザクションで使用されます。
楽観的ロックは、最初に業務操作を行い、最後に実際にデータが更新されたときにのみ、データが更新されたかどうかを確認します。Javaの並行パッケージのAtomicFieldUpdaterも同様で、これもCASメカニズムを使用し、データをロックせず、代わりにデータのタイムスタンプまたはバージョン番号を比較して楽観的ロックで必要なバージョン判定を実現します。
5. MySQLのその他の知識ポイント
-
一般に、MySQL の内部構造はどの 2 つの部分に分けることができますか?
これは、サービス レイヤーとストレージ エンジン レイヤーの 2 つの部分に分けることができます。
サービス レイヤーには、コネクタ、クエリ キャッシュ、アナライザー、オプティマイザー、エグゼキューターなどが含まれ、MySQL のコア サービス関数のほとんどと、すべての組み込み関数 (日付、時刻、数学、暗号化関数など) をカバーします。すべてのストレージ エンジン ストアド プロシージャ、トリガー、ビューなど、すべての機能がこの層で実装されます。
ストレージ エンジン層は、データの保存と取得を担当します。そのアーキテクチャ モードはプラグインであり、InnoDB、MyISAM、Memory などの複数のストレージ エンジンをサポートします。最も一般的に使用されているストレージ エンジンは InnoDB で、MySQL 5.5.5 以降のデフォルトのストレージ エンジンになっています。
-
undo ログ、redo ログ、および binlog の用途は何ですか
REDO ログは InnoDB エンジンに固有であり、エンジン内のテーブルの変更レコードのみを記録します。Binlog は MySQL のサーバー層によって実装され、すべてのエンジンの変更をデータベースに記録します。
REDO ログは、特定のデータ ページで行われた変更を記録する物理ログであり、binlog は、このステートメントの元のロジックを記録する論理ログです。
REDO ログは周期的に書き込まれ、スペースは常に使い果たされます; binlog ファイルは追加で書き込むことができます. binlog ファイルが特定のサイズに書き込まれると、次のログに切り替わり、前のログは上書きされません.
補充する
1. Redolog レコードの変更内容 (どのページが変更されたか) は、トランザクションの開始前に書き込まれ、データが削除されない前にデータベースがハングした後にデータの回復に使用されます。 transaction is commit
. 読み取り/書き込みの分離に使用可能
3、変更前のレコードを取り消し、ロールバックとマルチバージョンの同時実行制御に使用 -
バッファプールとは
Innodb ストレージ エンジンは、データベースの読み取りと書き込みのパフォーマンスを向上させるためにバッファー プール (*Buffer Pool*)を設計します。
- データを読み取るとき、データがバッファ プールに存在する場合、クライアントはバッファ プール内のデータを直接読み取ります。それ以外の場合は、ディスクから読み取ります。
- データを変更するときは、まずバッファ プール内のデータが配置されているページを変更し、次にそのページをダーティ ページとして設定し、最後にバックグラウンド スレッドによってダーティ ページをディスクに書き込みます。
何をキャッシュするか
InnoDB は、格納されたデータを複数の「ページ」に分割し、そのページをディスクとメモリの相互作用の基本単位として使用します。ページのデフォルト サイズは 16KB です。したがって、Buffer Pool も「ページ」で分割する必要があります。
MySQL が起動すると、InnoDB は Buffer Pool の連続メモリ スペースを適用し、
16KB
デフォルト サイズに従ってページを 1 つずつ分割します. Buffer Pool 内のページは キャッシュ ページ と呼ばれます. この時点で、これらのキャッシュ ページは解放されており、プログラムが実行されると、ディスク上のページがバッファー プールにキャッシュされます。Innodb は、3 つのリンクされたリストを介して低速ページを管理します。
- フリー リスト (フリー ページ リンク リスト)、フリー ページの管理。
- フラッシュ リスト (ダーティ ページ リンク リスト)、ダーティ ページの管理。
- ダーティ ページ + クリーン ページを管理する LRU List は、最近クエリを実行したデータと頻繁にクエリを実行したデータをキャッシュし、クエリの頻度が低いデータを削除します。;
InnoDB has made some Optimizations to LRU. 私たちがよく知っている LRU アルゴリズムは、通常、LRU リンク リストの先頭に最近クエリされたデータを置きますが、InnoDB は 2 つの最適化を行います。
- LRU リンクリストを若い領域と古い領域に分割します.バッファプールに追加されたページは,最初に古い領域に挿入されます.ページがアクセスされると,若い領域に入ります.目的は,読み取りの問題を解決することです.先の失敗。
- **「ページがアクセスされた」および「古い領域の滞留時間
innodb_old_blocks_time
がしきい値、ページは若い領域に挿入されます。それ以外の場合は、依然として古い領域に挿入されます。大量のホットデータを排除する問題であるバッチデータアクセスを解決することです。
innodb_old_blocks_pct
パラメータを調整することで、若い領域と古い領域の比率を設定できます。 -
DROP、DELETE、TRUNCATE の違い
3 つすべてが削除を表すことができ、微妙な違いは次のとおりです。
落とす 消去 トランケート SQL ステートメントのタイプ DDL DML DDL ロールバック ロールバックなし ロールバックできます ロールバックなし コンテンツを削除する データベースからテーブルを削除します。すべてのデータ行、インデックス、権限も削除されます テーブル構造はそのままです。テーブル内のデータ行のすべてまたは一部を削除してください テーブル構造はまだ残っています。テーブル内のすべてのデータを削除します 削除速度 最速の削除 削除は遅く、行ごとに削除する必要があります すばやく削除 したがって、テーブルが不要になった場合は DROP を使用し、一部のデータ行を削除する場合は DELETE を使用し、テーブルを保持したまますべてのデータを削除する場合は TRUNCATE を使用します。
-
SQL構文における内部結合、自己結合、外部結合(左、右、完全)およびクロス結合の違いは何ですか?
-
内部結合: 一致する 2 つの要素テーブルのみが結果セットに表示されます。
-
外部結合:
-
左外部結合: 左側が駆動テーブルで、駆動テーブルのすべてのデータが表示され、一致するテーブルの一致しないデータは表示されません。
-
右外部結合: 右側が駆動テーブルで、駆動テーブルのすべてのデータが表示され、一致するテーブルの一致しないデータは表示されません。
-
完全外部結合: 結合されたテーブル内の一致しないデータがすべて表示されます。
- 相互接続: デカルト効果、表示される結果は、リンクされたテーブルの数の積です。
-
-
MySQLのCHARとVARCHARの違いは何ですか
- char の長さは不変で、指定された長さまでスペースで埋められますが、varchar の長さは可変です。
- char のアクセス レートは、varchar のアクセス レートよりもはるかに高速です。
- char の格納方法は、英字(ASCII)で 1 バイト、漢字 1 文字で 2 バイトを占有します。varchar の格納方法は次のとおりです。各英字は 2 バイトを占有し、漢字も 2 バイトを占有します。
-
データベース内の主キー、スーパー キー、候補キー、および外部キーとは
- スーパーキー:リレーションシップ内のタプルを一意に識別できる属性セットは、リレーショナル スキーマのスーパーキーと呼ばれます
- 候補キー:冗長な属性を含まないスーパー キーは、候補キーと呼ばれます。つまり、候補キーでは、属性を削除するとキーではなくなります。
- primary key :ユーザーがタプル識別子として選択した候補キープログラムの主キー
- 外部キー:リレーショナル スキーマ R の属性 K が他のスキーマの主キーである場合、kはスキーマ R の外部キーと呼ばれます。
主キーは候補キーのサブセットであり、候補キーはスーパー キーのサブセットであり、外部キーの決定は主キーに関連しています。
-
MySQL の最適化
- 検索フィールドのインデックスを作成する
- Select * の使用を避け、クエリが必要なフィールドをリストします
- 縦割りテーブル
- 適切なストレージ エンジンを選択する
-
SQL文の実行処理
サーバー層が sql を順番に実行する手順は次のとおりです。
- クライアントのリクエスト ->
- コネクタ (ユーザーの認証、権限の付与) ->
- キャッシュのクエリ (キャッシュがあれば直接戻り、存在しない場合は後続の操作を実行) ->
- アナライザー (SQL の字句解析および構文解析操作) ->
- オプティマイザ(主に、実行されたSQL最適化に対して最適な実行計画方法を選択) ->
- Executor (実行時、まずユーザーに実行権限があるかどうかを確認し、次にこのエンジンが提供するインターフェースを使用します) ->
- エンジン レイヤーに移動してデータを取得します (クエリ キャッシュが有効な場合、クエリ結果がキャッシュされます)。
簡単な要約:
- コネクタ: 管理接続、権限検証。
- Query cache : キャッシュにヒットした場合、結果が直接返されます。
- アナライザー: SQL の字句解析と構文解析を実行します (クエリ SQL フィールドが存在するかどうかの判断もこのステップにあります)。
- Optimizer : 実行計画の生成、インデックスの選択。
- Executor : エンジンを操作し、結果を返します。
- ストレージ エンジン: データを保存し、読み取りおよび書き込みインターフェイスを提供します。
-
データベースの 3 つのパラダイムとは
- 最初のパラダイム: 列の原子性に重点が置かれます。つまり、データベース テーブルの各列は分割できない原子データ項目です。
- 第 2 正規形: エンティティの属性は、主キーに完全に依存する必要があります。いわゆる完全依存とは、主キーの一部のみに依存する属性が存在できないことを意味します。
- 第 3 正規形: 非キー属性は、他の非キー属性に依存しません。
-
MVCCの理解
データベースの同時実行シナリオ:
- 読み取り-読み取り: 問題はなく、同時実行制御の必要もありません。
- 読み取り/書き込み: スレッド セーフの問題があり、トランザクション分離の問題が発生する可能性があり、ダーティ リード、ファントム リード、繰り返し不可能なリードが発生する可能性があります。
- Write-Write: スレッド セーフの問題があり、更新が失われる可能性があります。
マルチバージョン同時実行制御 (MVCC) は、読み取りと書き込みの競合を解決するために使用されるロックフリーの同時実行制御です。つまり、一方向に増加するタイムスタンプをトランザクションに割り当て、変更ごとにバージョンを保存し、バージョンをトランザクションのタイムスタンプ 読み取り操作は、トランザクションが開始される前のデータベースのスナップショットのみを読み取ります。
MVCC は、データベースに関する次の問題を解決できます。
- データベースの読み取りと書き込みを同時に行う場合、読み取り操作中に書き込み操作がブロックされるのを回避できます。また、書き込み操作で読み取り操作をブロックする必要がないため、データベースの同時読み取りと書き込みのパフォーマンスが向上します。
- 同時に、ダーティ リード、ファントム リード、繰り返し不可能なリードなどのトランザクション分離の問題も解決できますが、更新が失われる問題は解決できません。
-
マスター/スレーブ レプリケーションに関係する 3 つのスレッドはどれですか?
主に、binlog スレッド、I/O スレッド、SQL スレッドの 3 つのスレッドが関係します。
- binlog スレッド: マスター サーバー上のデータ変更をバイナリ ログ (バイナリ ログ) に書き込む責任があります。
- I/O スレッド: マスター サーバーからバイナリ ログを読み取り、それをスレーブ サーバーのリプレイ ログ (リレー ログ) に書き込む役割を果たします。
- SQL スレッド: 再生ログを読み取り、その中の SQL ステートメントを再生します。
-
データベースが永続性を保証する方法
主にInnodb のredo ログを使用します。ログを書き換えます。前述のように、MySQL はまずディスク上のデータをメモリにロードし、メモリ内のデータを変更してからディスクに書き戻します。このときに突然シャットダウンすると、メモリ内のデータが失われます。この問題を解決するには?簡単です。トランザクションがコミットされる直前にデータをディスクに書き込むだけです。これを行うことの何が問題になっていますか?
- ページ内の 1 バイトだけを変更するには、ページ全体をディスクにフラッシュする必要がありますが、これはリソースの無駄です。結局のところ、ページのサイズは 16kb であり、少しだけ変更すると、16kb のコンテンツをディスクにフラッシュする必要があり、これは不合理に思えます。
- 結局、トランザクション内の SQL は複数のデータ ページの変更を伴う可能性があり、これらのデータ ページは隣接していない可能性があります。つまり、それらはランダム IO に属しています。明らかに、ランダム IO の動作は遅くなります。
したがって、上記の問題を解決するためにREDO ログを使用することにしました。データを変更するときは、メモリ上で操作するだけでなく、操作をREDO ログに記録します。トランザクションがコミットされると、REDO ログがフラッシュされます ( REDO ログの一部はメモリにあり、一部はディスクにあります)。データベースが停止して再起動すると、REDO ログの内容がデータベースに復元され、UNDO ログとbinlogの内容に従ってデータがロールバックまたは送信されます。
REDO ログを使用する利点は?
実際、REDO ログのフラッシュは、データ ページのフラッシュよりも効率的であるという利点があります。具体的なパフォーマンスは次のとおりです。
- REDO ログのサイズは小さい. 結局のところ、どのページが何を変更したかを記録するだけなので、サイズが小さく、すぐにフラッシュされます。
- REDO ログは、シーケンシャル IO に属する末尾に常に追加されます。効率は明らかにランダム IO よりも高速です。
-
データベースは原子性をどのように保証しますか
主にInnodb のundo ログを使用します。元に戻すログはロールバック ログと呼ばれ、アトミック性の鍵となります。トランザクションがロールバックされると、正常に実行されたすべての SQL ステートメントを元に戻すことができます。ロールバックしたい対応するログ情報を記録する必要があります。 . 例えば
- データを削除するときは、このデータの情報を記録する必要があり、ロールバックするときは、この古いデータを挿入する必要があります
- データを更新する場合は、以前の古い値を記録する必要があり、ロールバックする場合は、古い値に基づいて更新操作を実行します。
- データを挿入するときはこのレコードの主キーが必要で、ロールバックするときは主キーに従って削除操作を行います
undo ログには、これらのロールバックに必要な情報が記録されます。トランザクションの実行が失敗した場合、またはロールバックが呼び出されてトランザクションがロールバックされた場合、 undo ログの情報を使用して、データを変更前の状態にロールバックできます。
-
データベースはどのように一貫性を確保しますか
- データベース レベルから、データベースは原子性、分離、永続性を通じて一貫性を保証します。つまり、ACID の 4 つの特性のうち、C (一貫性) は目的、A (原子性)、I (分離)、D (持続性) は手段であり、一貫性を確保するためにデータベースが提供する手段です。データベースは、一貫性を実現するために AID の 3 つの特性を実装する必要があります。たとえば、アトミック性は保証できず、明らかに一貫性も保証できません。
- アプリケーション レベルから、データベース データが有効かどうかをコードで判断し、ロールバックするか、データを送信するかを決定します。
-
データベースの同時実行性を高めるためのソリューション
- Web サービス フレームワークにキャッシングを追加します。サーバーとデータベース層の間にキャッシュ層を追加することで、頻繁にアクセスされるデータをキャッシュに格納し、データベースの負荷を軽減します。
- データベース インデックスを増やして、クエリ速度を向上させます。(ただし、インデックスが多すぎると速度が遅くなり、データベースの書き込みによってインデックスの更新が発生し、これも速度が低下します)
- マスターとスレーブの読み取りと書き込みを分離し、マスターサーバーが書き込みを担当し、スレーブサーバーが読み取りを担当します。
- データベースを分割して、データベース テーブルをできるだけ小さくし、クエリの速度を向上させます。
- 分散アーキテクチャを使用して、コンピューティング プレッシャーを分散します。
-
データベース構造最適化の手段
- パラダイムの最適化: 冗長性の排除 (スペースの節約など)
- アンチパラダイム最適化: 適切に冗長性を追加する (結合を減らす) など
- データの範囲を制限する: データの範囲を制限する条件のないクエリ ステートメントを必ず禁止してください。たとえば、ユーザーが注文履歴を照会すると、1 か月以内にそれを制御できます。
- 読み取り/書き込みの分離: 従来のデータベース分割スキーム。メイン ライブラリが書き込みを担当し、スレーブ ライブラリが読み取りを担当します。
- 分割テーブル: パーティションはデータを物理的に分離し、異なるパーティションのデータを指定して、異なるディスクのデータ ファイルに保存できます。このように、テーブルがクエリされるとき、完全なテーブル スキャンの代わりにテーブル パーティションをスキャンするだけでよく、クエリ時間が大幅に短縮されます. さらに、異なるディスク上のパーティションは、このテーブルのデータ転送も分散します.ディスク I/O の場合、適切に設計されたパーティションは、データ転送をディスク I/O 競合に均等に分散できます。この方法は、データ量の多い時刻表に適用できます。テーブル パーティションは、月単位で自動的に作成できます。
-
リレーショナル データベースと非リレーショナル データベースの違い
非リレーショナル データベースは NOSQL とも呼ばれ、キーと値のペアの形式で格納されます。
読み取りと書き込みのパフォーマンスが高く、拡張が容易で、Redis、Mongodb、HBase などのメモリ データベースとドキュメント データベースに分割できます。
非リレーショナル データベースを使用するシナリオ:
- ログ システム、地理的な場所のストレージ、膨大なデータ ボリューム、高可用性
- リレーショナル データベースの利点
- 理解しやすい。リレーショナル モデルを使用してデータを整理するためです。
- データの一貫性を保つことができます。
- データ更新のオーバーヘッドは比較的小さいです。
- 複雑なクエリ (where 句を含むクエリ) のサポート
- 非リレーショナル データベースの利点
- SQL層で解析する必要がなく、読み書き効率が高い。
- キーと値のペアに基づいて、データのスケーラビリティは非常に優れています。
- 写真や文書など、さまざまなタイプのデータの保存に対応できます。
-
データベースをデータベースとテーブルに分割する理由
サブデータベースとサブテーブルの目的は、データベースの単一データベースと単一テーブルの負担を軽減し、クエリのパフォーマンスを向上させ、クエリ時間を短縮することです。
テーブルを分割することにより、データベース内の単一のテーブルの負荷を軽減し、別のテーブルに負荷を分散できます.同時に、別のテーブルのデータ量が少ないため、クエリのパフォーマンスを向上させ、時間を短縮できます.クエリ時間さらに、テーブル ロックの問題を大幅に軽減できます。テーブル分割戦略は、垂直分割と水平分割として要約できます。水平分割: モジュロ分割はランダム分割に属し、時間次元分割は連続分割に属します。垂直分割の設計方法、私の提案: 一般的に使用されていないフィールドを別の拡張テーブルに分割する テキストが大きいフィールドを別の拡張テーブルに分割し、頻繁に変更されないフィールドを同じテーブルに配置する頻繁に変更されるフィールドを別のテーブルに配置します。多数のユーザー シナリオの場合、モジュールとサブテーブルを使用することを検討できます. データは比較的均一であり、ホット スポットや同時アクセスのボトルネックが発生しにくい.
ライブラリ内のサブテーブルは、1 つのテーブル内のデータが大きすぎるという問題を解決するだけですが、1 つのテーブル内のデータを異なる物理マシンに分散するわけではないため、MySQL サーバーへの負荷を軽減することはできません。同じ物理マシンでのリソースの競合と、CPU、メモリ、ディスク IO、ネットワーク帯域幅などのボトルネック。
サブデータベースとサブテーブルによってもたらされる分散ジレンマと対策データの移行と拡張の問題 - 一般的なアプローチは、最初にプログラムを介してデータを読み取り、次に指定されたサブテーブルに従って各サブテーブルにデータを書き込むことです戦略中盤。ページングと並べ替えの問題----さまざまなサブテーブルのデータを並べ替えて返し、さまざまなサブテーブルから返された結果セットを要約して再並べ替えし、最終的にそれらをユーザーに返す必要があります。