記事ディレクトリ
消去
- innodb_file_per_table = ON: テーブル データは、共有テーブル スペースではなくファイルに存在します。
- drop: データをクリアし、テーブル構造を削除します。
- truncate :テーブルを削除して再作成し、自動インクリメント列をリセットします。
- 削除: データを 1 つずつ削除し、記録された位置を再利用可能としてマークし、ディスク上のファイルが小さくなって穴が生じないようにします。
- ランダムに挿入すると、ページが分割されて穴が開くこともあります。
- データベースを削除してデータを復元する方法。
最適化
再作成
alter table A engine=InnoDB
ロックテーブル ddl
- バージョン 5.5 より前。
- 一時テーブルにデータを挿入する場合、業務書き込みは禁止されています。
オンライン ddl
- 5.6以降。
- ステップ:
- 一時ファイルを作成し、テーブル A の主キーのすべてのデータ ページをスキャンします。
- データ ページのテーブル A のレコードを使用して B+ ツリーを生成し、一時ファイル tmp に保存します。
- 一時ファイルの生成プロセス中に、A に対するすべての操作がログ ファイル (行ログ) に記録されます。これは、図の state2 の状態に対応します。
- 一時ファイルが生成された後、ログ ファイル内の操作を一時ファイルに適用して、表 A と同じ論理データを含むデータ ファイルを取得します。これは、図の状態 3 の状態に対応します。
- テーブル A のデータ ファイルを一時ファイルに置き換えます。
- オンライン ddl の詳細な手順
- MDL 書き込みロックは、データをコピーする前に読み取りロックに縮退し、読み取りと書き込みをブロックせず、他の DDL を禁止します。
- オープン ソースの gh-ost をお勧めします。
比較した
- 再作成: テーブルを再作成します。
- テーブルを再構築するとき、 InnoDB は後続の更新のために各ページの 1/16 を予約し、テーブルは再構築後に最もコンパクトではありません。
- 分析テーブル: テーブルのインデックス情報を再統計し、データを変更せず、MDL 読み取りロックを追加します。
- テーブルの最適化 : 再作成+分析。
カウント
いくつかのカウント方法
- MyISAM はディスク上のテーブルに合計行数を格納し、実行中にこの数を直接返します。トランザクションはサポートされていません。
- Innodb は、エンジンから行ごとにデータを読み取り、それらを蓄積する必要があります。パフォーマンスが悪い。
- トランザクションをサポートし、複数のバージョンがあり、ビューと表示可能なレコードは実行時にのみ決定できます。
- 最小のインデックス トラバーサルを取得します。
- show table status: 推定値、不正確。
- 追加されたカウント テーブル: 単一のデータベース トランザクションが一貫性を保証します。
カウントの原則
- サーバー層は、必要なものを何でも提供します。
- InnoDB は必要な値のみを提供します。
- 現在のオプティマイザーは、count(*) のセマンティクスを最適化して「行数を取得する」だけで、他の「明らかな」最適化は行いません。
カウント機能比較
- カウント (フィールド):
- InnoDB はテーブル全体を走査し、フィールドを読み取ります。
- サーバー層がフィールドを取得した後、フィールドが null でない場合は直接蓄積され、そうでない場合は null ではないと判断されて蓄積されます。
- カウント (主キー ID):
- InnoDB はテーブル全体を走査し、各行の id 値を取り出してサーバー層に返します。
- サーバー層が ID を取得した後、行ごとに直接累積します。
- カウント(1):
- InnoDB は、値を取得せずにテーブル全体をトラバースし、各行に対して 1 を返します。.
- サーバー層が ID を取得した後、行ごとに直接累積します。
- count(*): 特別に最適化され、行ごとの累積の count(1) と同じです。
注文
CREATE TABLE `t` (
`id` int(11) NOT NULL,
`city` varchar(16) NOT NULL,
`name` varchar(16) NOT NULL,
`age` int(11) NOT NULL,
`addr` varchar(128) DEFAULT NULL,
PRIMARY KEY (`id`),
KEY `city` (`city`)
) ENGINE=InnoDB;
select city,name,age from t where city='杭州' order by name limit 1000 ;
すべてのフィールドを並べ替える
- ステップ:
- 条件を満たすレコードの主キーをインデックスで検索します。
- テーブルに戻り、クライアントに返す必要がある列を確認し、sort_buffer を書き込みます。
- メモリの並べ替え。必要なメモリが sort_buffer_size を超える場合は、一時ファイル マージ ソートを使用します。
- 最初の n 行を返します。
ROWIDソート
- データ行が長すぎて max_length_for_sort_data を超えています。並べ替える必要がある列と主キーのみを並べ替え用の sort_buffer に入れます。
- ステップ:
- インデックスで条件を満たすレコードの主キーを見つけます。
- テーブルに戻り、ソートが必要な列と主キーを確認し、sort_buffer を書き込みます。
- メモリの並べ替え。必要なメモリが sort_buffer_size を超える場合は、一時ファイル マージ ソートを使用します。
- 最初の n 行は、主キー ID を使用してテーブルに戻り、必要な列をチェックします。
- クライアントに戻ります。
メモリが十分にある場合は、できるだけメモリを使用してディスク アクセスを減らします。
行 ID の並べ替えがもう一度テーブルに戻り、ディスクがもう一度読み取られる可能性があります.Mysql はフィールド全体の並べ替えを優先します.
ソートされていません
- 元のデータの順序が間違っているため、MySQL は一時テーブルを生成し、一時テーブルで並べ替え操作を実行する必要があります。
- (city, name) インデックスがある場合は、データがフィルタリングされた後にデータが正しいことを確認し、直接トラバースして必要なレコードの主キーを取得し、テーブルに戻って結果を取得できます。
- (都市、名前、年齢) のインデックスがある場合は、テーブルを返さないようにインデックスを上書きできます。
加入
- 被駆動テーブル インデックスを使用できる場合は結合できますが、使用できない場合は結合しないようにしてください。
- 結合する場合は、小さなテーブル (それぞれの条件に従ってフィルター処理され、結合に参加するデータの合計量が少ない) を駆動テーブルとして使用します。
- 結合の分類、結合の最適化。
インデックスの入れ子ループ結合
- 被駆動表 t2 のインデックスを使用できます。
- ドライバー テーブル t1 のテーブル全体をスキャンし、 t2 のインデックスを1 つずつ検索します(BKA アルゴリズムは join_buffer 最適化を使用して t2 をバッチで検索します)。
ネストされたループ結合をブロックする
- 被駆動テーブル t2 で使用できるインデックスはありません。
- join_buffer 一時ストレージ。
- t1 は結合バッファを読み取ります。
- t2 をスキャンし、結合バッファ内のデータと 1 つずつ比較し、条件を満たす結果セットを取得します。
- join_buffer が join_buffer_size を超える場合、デフォルトは 256k で、t1 をセグメントに入れ、t2と joinbuffer をスキャンして結果セットを比較します。
- システムへの影響:
- t2 は複数回スキャンされるため、圧力は .
- 結合を判断するには、M*N 比較、CPU 圧力が必要です
- t2 のスキャンが 1 秒以上続くと、すべての t2 が若い領域に入り、バッファー プールの通常のサービス ヒット率が低下します。
- BKA 最適化は、一時テーブルにインデックスを追加することでトリガー できます。
- スレッドには、スレッドの終了時に再利用される一時テーブルがあります。
グループ化
基本的なプロセス
- m、c、主キー mを含むメモリ一時テーブル (メモリが十分でない場合はディスク支援) を作成します。
- インデックス a をスキャンし、id%10 に従って一時テーブルに c を蓄積します。
- m に従ってソートします。
使用の原則
- group by と group by null の並べ替え要件はありません。
- GROUP BY はなるべくインデックスを使用するので、データが揃っているので、一時テーブルやソートを避け、読み込みながら結果を出力することができます。
- Group by は可能な限りメモリ一時テーブルを使用し、tmp_table_size はメモリ一時テーブルの上限を調整します。
- データ量が多すぎる場合、ダイレクトSQL_BIG_RESULT はディスク一時テーブルを使用します。