Javaのロックカテゴリー
ロックカテゴリ
- ロックフェア/不公平ロック
- リエントラントロック
- 排他ロック/共有ロック
- ミューテックス読み取り/書き込みロック
- 楽観/悲観的ロックをロック
- セグメント化されたロック
- 偏ったロック/ロック軽量/ヘビー級ロック
- スピンロック(ほぼすべての使用java.util.concurrentパッケージの下にロック)
CAS
これは、パフォーマンスの低下の原因ロックの使用が解決マイナーの競合にシナリオをマルチスレッドです一种机制
。まず比较
、あなたは、期待を満たしていない場合重试
。これは3つの動作している内存位置
要因を:、预期原值
と新值
。元の値の予想されるメモリ位置の値がプロセッサに等しい場合、位置の値が等しくない場合、現在の値を取得するために、新しい値に更新し、その後、投票の結果がある閾値出口に達するまで動作し続けています。
AQS
AbstractQueuedSynchronizer
頭字AQS同期フレームは、抽象状態依存シンクロナイザを実装するために使用されてもよいです。JDK1.5が設けjava.util.concurrent
パケット同期最も(Synchronizer)
ようLock, Semaphore, Latch, Barrier
に基づくもののような、java.util.concurrent.locks.AbstractQueuedSynchronizer
クラスのフレームの実装。
乐观锁/悲观锁
乐观锁
:オプティミスティック・ロックは、という楽観的な考え方である读多写少
同時に遭遇する可能性が低い、時間とデータを取るたびに不会上锁
、他の人が変更されていないと思うので、。誰もが、このデータを更新しないの書き込みに時間がかかりますがある場合でも、裁判官が更新され读取版本号然后加锁
、主に上一次版本号进行比较
このデータが更新されるかのように同じではありませんが、読み取りを繰り返すことになる場合には、比較して、書き込み操作。基づいてCAS
達成します。悲观锁
:悲観論、考えて写多读少
、比較的高い経験する可能性によって複雑に書き込み、各読み取りおよび書き込みデータはロックされますが、別のスレッドが取得するためにロックされるまでブロックします書きたいです。Javaは悲観的にロックされSynchronized
、AQS(AbstractQueuedSynchronizer)
フレーム内のロックが少ない、など、悲観的ロックに変換され得る楽観的ロックロックCAS取得する最初の試みですRetreenLock
。
公平锁与非公平锁
フェアロックは:アプリケーションロックロックを取得するために、スレッドの数を指します。
アンフェアロック:複数のスレッドが前のアプリケーションよりもロック・スレッドへの優先アクセスを適用した後に可能であり、スレッドはアクセスリソースと現象が永遠に実行することができないことはできません飢餓を引き起こす可能性が、ロックロックを適用するために取得していません。
RetreenLock
これは、ロック機能が公正、公平、デフォルト以外のロックではない構成することによって決定されます。フェアロックよりも大きいスループット不公平ロック。Synchronized
非フェアロックは、それは、AQSによるスレッドスケジューリングを実現していなかった公正ロックになることはできません。//默认创建是非公平锁 public ReentrantLock() { sync = new NonfairSync(); } //通过bool值来控制是否是公平的还是不公平的,为true公平锁,为false不公平锁 public ReentrantLock(boolean fair) { sync = fair ? new FairSync() : new NonfairSync(); }
可重入锁
- また、再帰的ロックとして知られ、スレッドがロックを取得するために繰り返すことができ、同じスレッドが外層方法でロックを取得し、この方法は、自動的に内部ロックに入るであろう。
synchronized
そして、ReentrantLock
リエントラントロックされ、ロックはデッドロックがある程度の再入を避けることができます。
独享锁与共享锁
- 排他ロックは唯一のスレッドによって保持させることができるロックを指し、
- ロックが保持同時に複数のスレッドで共有することができ
synchronized
かつReentrantLock
排他ロックされ、ReadWriteLock
ロックが共有読み取りロックで、書き込みロックは排他ロックであり、ReentrantLock
排他ロックと共有ロックを経由もあるAQS
達成します。
互斥锁与读写锁
- 実際、排他ロックと共有ロックの特定の声明では、ミューテックスは、Javaで実装さ
ReentrantLock
れ、読み書きは、Java実装であるロックReadWriteLock
。
分段锁
- ロックは本質的に
策略
、ロックは特定できません。ためConcurrentHashMap
JDK 11がロッキングセグメントを介して実現される前に、同時実行が達成されます。あなたは、全体ではなくハッシュマップロックするのではなく、セグメントロックにそのセグメントでのhashCodeのノウハウにより、要素を配置する必要がある場合。長い要素は同一のセグメント領域に配置されていない場合などのように、マルチスレッドでは、素子を並列に挿入することができ、時間は、ロックセグメントのすべての統計サイズを取得するために必要。最終的にロックセグメントがロック粒度を改良するために使用されます。
偏向锁
- 限り、要求がロックされて始めから終わりまでスレッド。自動スレッドがロックを取得し、スレッド同期コードアクセスされました。JavaはロックJava6の導入マルチスレッド最適化されて付勢。これは、プロセスは、唯一のスレッドアクセス、マルチスレッドのための無競合を実行している場合、同期せずにスレッドが、この時間は、スレッドがロックバイアスに追加され、ロック・スレッド第一アクセスする傾向があります。しかし、他のスレッドが占めてロックが発生した時間が再び実行され、保持しているバイアスロッキングスレッドが中断され、JVMは、その本体が軽量ロックとしてロックのエスカレーションをロックバイアスされなくなります。
バイアスされたロックアプリケーションのシナリオ
- 常に同期ブロックを実行するだけつのスレッドは、それが実行する前に完了していない、実行する他のスレッドは、ロックは競争ではないではありませんが、競争に、軽量ロックにアップグレードされます。それは取り消された場合、それが引き金となり、軽量ロックアップグレードする時が来た
stop the world
操作を。
世界を停止するにははじめに
- Javaは、
Stop-The-World
機構はSTWと呼ばれる、場合ガベージコレクションアルゴリズム、Javaアプリケーション内の他のすべてのスレッドが(ガベージコレクションヘルパー外以外)中に懸濁されていることです。ホリスティックな、グローバルな一時停止中のJavaポーズ現象、すべてのJavaコードを停止し、native
コードを実行することができますが、できない相互作用JVMを持ちます。
轻量级锁
- 偏ったロックからのアップグレード、偏ったロッキングスレッドがsynchronizedブロックに入ったときに、この時間は別のスレッドのロック競合を追加し、それは軽量ロックにアップグレードされます。複数のスレッドが、競争のケースなしで、Java仮想マシンが目詰まりを避けるために、軽量ロックを使用し、ヘビー級ロックウェイクを繰り返すことになりますされ、異なる期間で同じロックを要求します。
軽量ロック解除
- リリース中の場合は軽量ロック、ロックは、ロックを取得する際には、オブジェクトヘッドmarkWordをコピーする前に、それ自体が他のことでロックを保持していたときに、ロックが解除され、ヘビー級ロックに軽量から切り替えられますスレッドへのアクセス、およびこのスレッドmarkword両方コントラスト矛盾はヘビーロックにスイッチを発見され、修正され。
重量级锁
- これは、ロックされたスレッドのJava仮想マシンの故障を遮断、この状態では、Javaでのロックの基礎であり、かつターゲットロックが解除されたときに、これらのスレッドを覚まします。Javaは、
synchronized
ヘビー級のロックの一種です。リリース中の場合は軽量ロック、それはオブジェクトヘッダマークのWordのコピーを取得する前にそれをロック、ヘビー級のロックロックに軽量から切り替わります、それは自身がロックを保持している見つけたとき、ロックを解除します他のアクセスのスレッド、およびマークワードにこのスレッドは矛盾がロックへの切り替え2ヘビーFOUND間のコントラストを変更されています。ブロックのパフォーマンスに他のアプリケーションを作るためにヘビー級スレッドロック。
Javaオブジェクトのヘッダとは何ですか
- Javaオブジェクトのヘッダ情報は、2つの部分、すなわち、含む
Mark Word
メタデータポインタを、Mark Word
例えば、実行時にデータオブジェクトを格納するためにHashCode
、ロックステータスフラグは、Gcの世代年齢スレッドがロックを保持し、メタデータポインタがのための方法に向けられていますメタデータターゲットクラス領域は、特定のオブジェクトは、メタデータの種類によって決定することができます。
自旋锁
- 非常に短時間でロックを解除することができ、ロックを保持しているスレッド、および競争上のロックを待っているそれらのスレッドがブロックされて保留状態に入るように、カーネルモードとユーザーモードの間で切り替える必要がないとき、彼らは唯一のスピンを待つ必要があります等スレッドはロックロックがスレッドコンテキストスイッチングを減らす、直ちに取得することができる保持するロックを解放した後。しかし、サイクルが増加し、CPUの消費が発生します。
廃棄物のCPUを解決するためのオプションのロック
- ロックは非常に競争力がある、またはロックを保持しているスレッドがロックブロックを保持して同期を実行するには長い時間がかかるロックを取得する前に、スピンロックが占有、有用な作業を行うためのCPUを占有してきたので、この時間は、使用スピンロックに適していない場合CPUは、この時間に競争の中で多数のスレッドロックをしませんでした、そして、ロックは長い時間を得ることになり、消費がスレッドスピンスレッドがかかる操作保留中のブロックされているよりも大きいこと、および他のニーズカップスレッドが引き起こし、CPUに取得することはできませんCPUの無駄。したがって、この場合には、我々はスピンロックを閉鎖しなければなりません。
https://cloud.tencent.com/developer/article/1560084からオリジナルの引用