私たちは、最初の主要な前提がある知っている必要があります。mysqlロックを達成するために特定のストレージエンジンです。だから、デフォルトのエンジンのMyISAMとサードパーティ製のプラグロックMySQLの実装機構のInnoDBエンジンのように異なっています。
テーブルレベルロック、ページレベルのロック、行レベルのロック:MySQLは、ロック3つのレベルがあります
まず、定義
- 各時間は、ロックは、データロック機構の行は行レベルロック(ローレベル)です。行レベルのロックは、MySQL独自の方法をロックされていないが、他のストレージエンジンによってそれ自体が実装さ
第二に、長所と短所
1.メリット
- 小型ロック競合率、高い同時実行します。
2.欠点
- 複雑な、大きなオーバーヘッドを実装します。
- デッドロックが発生しやすい、遅いロック
第三に、ストレージエンジンをサポート
- 主InnoDBストレージエンジンの使用行レベルのロック、およびMySQL分散ストレージエンジンNDBCLUSTER
第四に、行レベルのロックタイプ
InnoDBテーブルの行レベルのロックは、2つのタイプに分けられる:共有ロックと排他ロック、および行レベルのロックとテーブル・レベルのロックを可能にするために、実装プロセスのロック機構で共存し、InnoDBはまた、使用意図的ロック(表レベルのロックを)のコンセプトは、我々は両方の共有意図的ロックと意図排他ロックを持っています。
トランザクションがリソースへのアクセスをロックする必要がある場合意向ロックの役割であり、排他ロックは、トランザクションが上記の表に適したロック意図的ロックの行を追加する必要がありますときに必要なリソースは、彼らが占有されている場合。彼らは共有ロックが必要な場合は、その後にテーブルトップを追加する意図共有ロック。彼らが必要とする場合や行(またはいくつかの行が)にテーブルトップを追加するまず、排他ロックの上に追加された意図排他ロック。
一つだけが存在している間テント共有ロックは、より多くの、しかし意図排他ロックを共存させることができます。そこで、我々は、InnoDBの言うことができる锁定模式实际上可以分为四种
:共享锁(S)
、排他锁(X)
、意向共享锁(IS
)と意向排他锁(IX)
互換モードをロック:
第五に、行レベルのロックの実装
インデックス上のInnoDB行ロックを与えることである索引项加锁
達成します。したがって、インデックスのみの条件を介してデータを取得するには、InnoDBは唯一の行レベルのロックをそうでなければ、InnoDBは表ロックを使用します。その他の考慮事項:
- インデックス条件を介していないクエリは、InnoDBのテーブルロックは、代わりに行ロックを使用する場合。
- MySQLの行ロックがインデックスに加えて、いないレコードロックプラス、そうであっても、レコードのアクセス異なる行のためにロックされているので、あなたが同じインデックスキーを使用している場合も、競合がロックします。
- テーブルは、インデックスを複数有する場合、異なるトランザクションは、異なる屈折率の異なる行でロックすることができ、さらに、主キーインデックスを使用するかどうか、一般的な索引または一意のインデックスは、InnoDBの行ロックがデータをロックするために使用されます。
- でも、インデックスフィールド内の条件ではなく、実施計画の異なる裁判官でのMySQLのコストによって決定された特定のデータを取得するためにインデックスを使用するかどうか、MySQLの全表スキャンは、このようないくつかの小さなテーブルとして高効率を、と思われる場合、それ使用のInnoDBテーブルロックの代わりに、行ロックは、この場合には、インデックスを使用しないであろう。ロック競合を分析する際したがって、インデックスの実際の使用を検証するためのSQLの実行計画をチェックすることを忘れないでください。
暗黙ロック:
- InnoDBの自動ロックの意図。
- UPDATEのために、DELETEとINSERT文、自動的にデータのセットに追加InnoDBがに関する
排他锁(X)
。 - 通常のSELECT文の場合、InnoDBはすべてのロックを追加しません。
ロックを表示します:
- 共有ロック(S):
SELECT * FROM table_name WHERE ... LOCK IN SHARE MODE
- 排他ロック(X):
SELECT * FROM table_name WHERE ... FOR UPDATE
SELECTと...共用モードで主にレコードが存在する行を確認するために必要なデータの依存関係で使用される共有ロックを取得し、動作を確認し、このレコードの更新には1または削除します。
現在のトランザクションが、操作を更新するレコードを必要とする場合しかし、更新操作を必要とするアプリケーションのための行をロックした後、あなたが排他ロックを取得するために、UPDATEの道... FOR SELECTを使用する必要があり、デッドロックが発生する可能性があります。
InnoDBテーブルロックを追加する方法:
トランザクションの終了前に、UNLOCKテーブルはテーブルのロックを解除し使用していない、UNLOCKテーブルが暗黙的にトランザクションをコミットしているため、InnoDBのテーブルロックにLOCK TABLESを使用している場合は、それ以外の場合は、MySQLのテーブルロックを与えることはありません、AUTOCOMMITを0に設定するには、に注意を払う必要があります; COMMIT、またはROLLBACKロックテーブルテーブルロックを追加することによって解除することができない、ロックはテーブルUNLOCKテーブルによって解放されなければなりません。
SET AUTOCOMMIT=0;
LOCK TABLES t1 WRITE, t2 READ, ...;
[do something with tables t1 and t2 here];
COMMIT;
UNLOCK TABLES;
- 1
- 2
- 3
- 4
- 5
彼らは、テーブルをロックするので、MyISAMのエンジンは、それをどのように選択していません!
六、ロックギャップ(ネクストキーロック)
1.ロック正義のギャップ:
データの最初のインデックスキーロックの前にルールをロックすることにより、InnoDBは達成最後のキーのインデックスの後に空間的および空間に関する情報をマーク記録しました。このINNODBロック実装が「ネクストキーロック」(として知られている间隙锁
)場合にスコープクエリ実行を通して見るので、キーが存在しない場合であっても、全体の範囲内のすべてのキーのインデックスをロックします。
例:emp表のみEMPID値であり101を、記録した場合は1,2、...、100、101、以下のSQL:
mysql> select * from emp where empid > 100 for update;
- 1
検索条件の範囲であり、InnoDBはない唯一の基準値の記録を満たす「ギャップ」ロックに(これらのレコードが存在しない)もより大きく101 EMPIDの、101をロックEMPID。
2.ギャップロック短所:
- いくつかの無実のキーがロックされますがない場合でも、キーロックの範囲、およびキー値の範囲内の任意のデータをロックロックに挿入することができないときのギャップロックは、つまり、より多くの致命的な弱点を持っています。偉大な害性能を引き起こす可能性がありますいくつかのシナリオで
- クエリは、インデックスを使用できない場合、InnoDBは、行レベル・ロックの使用を放棄し、減少並行処理性能が得られ、テーブルレベルのロックに切り替えます。
- インデックスはQuueryは、すべてのフィルタを使用含まれていない場合、データの一部にインデックスデータ検索キーポイントは、クエリがランク結果セットの一部ではないかもしれないが、ロックのギャップので、ロックされ範囲ではなく、特定のインデックスキーよりも、です。
- インデックスキーがロックされるように、同じデータが異なる行アクセス時間(フィルタ条件の指標は一部のみ)を使用する場合、クエリは、インデックスの場所データを使用する場合場合
3.ギャップロックアクション:
- 関連する要件を満たすためにファントム読み取り、分離レベルを防ぎます。
- データを復元して複製する必要があるためです。
4.注意
- 特にアプリケーションの同時挿入比較的多数で実用的なアプリケーションの開発では、我々はレンジ条件の使用を避け、更新されたデータにアクセスするために同じ条件を使用しようと、ビジネス・ロジックを最適化しようとする必要があります。
- 条件はロックが存在しない記録要求に等しい場合、ギャップはInnoDBのロックも使用されているロック外部条件の範囲によって以外ギャップ、InnoDBのロック。
セブン、行レベルのロック競合を参照
SQLを実行します。mysql> show status like 'InnoDB_row_lock%';
mysql> show status like 'InnoDB_row_lock%';
+-------------------------------+-------+
| Variable_name | Value |
+-------------------------------+-------+
| InnoDB_row_lock_current_waits | 0 |
| InnoDB_row_lock_time | 0 |
| InnoDB_row_lock_time_avg | 0 |
| InnoDB_row_lock_time_max | 0 |
| InnoDB_row_lock_waits | 0 |
+-------------------------------+-------+
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
あなたはより深刻なロックの競合を見つけた場合、それはまた、競合をロックすることができたInnoDBモニタを設定すること等により、さらに観測テーブル、行を発生し、原因にロック競合を分析します。以下のような:
モニターセット:mysql> create table InnoDB_monitor(a INT) engine=InnoDB
;
閲覧数:mysql> show engine InnoDB status
;
ビューを停止しますmysql> drop table InnoDB_monitor
。
特定の参照:InnoDBのモニター
八のデッドロック
デッドロックは何か:私はロックを解除するために、あなたがロックを解除するために、私は待って、待ってデッドロックを形成することになります。
デッドロックを見つける方法:InnoDBはトランザクション管理やロック機構を、デッドロックを検出するための特別な機構があり、非常に短い時間でデッドロックがシステムで検出された後、デッドロックの存在を持っています
ソリューション:
- トランザクションのロールバックの少ない方
- REPEATABLE-READ分離レベルでは、2つのスレッドが同時にSELECTと同じ条件を記録している場合... UPDATEプラス排他ロックの場合は、ケースを記録する条件の遵守が存在しない場合に、2つのスレッドが成功をロックします。それが存在しないレコードを見つけ、それは2つのスレッドが実行している場合、デッドロックが存在します、新しいレコードを挿入しようとします。この場合、COMMITTED分離レベルのREADを変更する、問題を回避することができます。
分析トランザクションサイズ:各トランザクションの挿入、更新またはデータ量を削除
注意:
- デッドロックのシーンがInnoDBストレージエンジンを超えて関与する場合、InnoDBはこのデッドロックを検出する方法はありません、この時間はわずかタイムアウトlimitパラメータは解決するためにロックすることでInnoDB_lock_wait_timeoutことができます。
九、行レベルのロックを最適化します
InnoDBストレージエンジンは、行レベルのロックを達成するために、テーブルレベルのロックよりも性能コストを達成する機構をロック中は高くなるかもしれないが、全体的な並行処理能力の点でMyISAMテーブルレベルよりもはるかに優れていますロックされました。並行処理の量、InnoDBテーブルとMyISAMの全体的なパフォーマンスは明らかな利点が比較されますと、システムが高い場合。しかし、行レベルのロックInnoDBはまた、我々は不適切に使用される場合、それはInnoDBの全体的なパフォーマンスがMyISAMテーブルよりも高くすることができず、さらに悪いことができるだけでなくことがあり、その弱い側面を有しています。
(1)InnoDBの行レベルロックの使用の合理化には、その弱点を避けるために、我々は行う必要があり、以下:
A)可能な限り、あなたがロックし、インデックスによるキーことができないので、すべてのデータの取得は、InnoDBのを避けるために、インデックスを介して行われますようにテーブル・レベルのロックにアップグレードし、
インデックスのb)の合理的設計ので、できるだけ正確に時間の上に屈折率のInnoDBロックキー狭いロック範囲、ロック不要を避けるために、他のクエリの実行に影響を与える;
C)可能フィルタ条件に基づいてデータ検索の範囲を減少させる、ロックをもたらすためにギャップの悪影響を回避するロックされたレコードをロックしてはならない;
D)は、トランザクションのサイズ、ロックの長さとロック時間を短縮するリソースの量を制御しようと;
E)ビジネス環境でMySQLのトランザクション分離レベルの実現をもたらしますので、追加のコストを削減するために、低トランザクション分離レベルの使用は、可能な限り、どこを可能にしました。
:(2)によりInnoDBの行レベルのロックおよびトランザクションのために、それは確かに、次のヒントは、より一般的にデッドロックが発生する確率を減少させるために使用されるの一部であり、デッドロックを生成する
同じアクセスシーケンスに従って可能な限り、A)同様のサービスモジュール;デッドロックを防ぐために、アクセス
b)は同じトランザクション内で、デッドロックの可能性を低減するために必要なすべてのリソースに一度できるだけロックを、
事業の一部がデッドロックすることは非常に傾向があるため、C)、あなたはロックをアップグレードしようとすることができます粒子サイズは、テーブルのレベルをロックすることによって、デッドロックの可能性を低減します。