synchronized キーワードは、Java 同時プログラミングで一般的に使用される同期ロックです。メソッドまたはコード ブロックをロックするために使用されます。コード ブロックをロックする場合は、synchronized(this){}、synchronized(Object){}、synchronized を使用できます。 (クラス) {}。
#ロックされたコンテンツが実行されるか、実行中に例外がスローされると、ロックは自動的に解放されます。
手動でロックを解放したい場合は、ロックされたオブジェクトの wait() メソッドを呼び出してロックを解放して待機状態にし、他のスレッドに切り替えて実行する必要があります。 () メソッドは、他のスレッドの wait() メソッドと呼び出されたオブジェクトを起動するだけですが、ロックは解放されず、選択順序はコードによって制御されず、仮想マシンによって実装されます。
したがって、オブジェクトの wait()、notify()、および NoticeAll() メソッドは、スレッド間のスケジューリングを完了するために synchronized キーワードとともにのみ使用できます。
ロックされたメソッドは、次のように synchronized(this){コード ブロックとしてのメソッドのすべてのコード} と同等です。
public synchronized void test() { ... }
上記と同等たとえば、ロックされている例は、このクラスのオブジェクトです。静的メソッドがロックされている場合、その静的メソッドはオブジェクトではなくクラスに属していることがわかります。したがって、synchronized によって変更された静的メソッドは、このクラスのすべてのオブジェクトをロックします。 、このクラスに属している限り、2 つの Instance オブジェクトであってもロックされます。
public void test() { synchronized (this) { ... } }
public synchronized static void test() { ... }
と同等 コード ブロックをロックするときの参照オブジェクトがロック メソッドであっても、コード ブロックであっても、1 つの原則を覚えていれば明らかです。つまり、参照オブジェクトが同じである場合にのみ同期ロックが機能し、それ以外の場合、ロックは相互に排他的ではなく、同時に実行できます。
synchronized(this) は、現在のクラスのオブジェクト インスタンスが同じである場合にロックが有効になることを示し、synchronized(Object) は、Object オブジェクトが同じである場合にロックが有効になることを示し、synchronized(class ) は、すべてが同じクラスである場合にロックが有効になることを示します。
簡単な例を示します:
public static void test() { synchronized (所在类.class) { ... } }
上記のコードでは、参照オブジェクト str は "1" です。Java では、文字列文字列が this.str="1" を渡すと、代入は次のようになります。 str=String.valueOf("1") と同等。文字列 "1" が以前に初期化されている場合は、前のものが直接取得されるため、同じオブジェクトになります。上で紹介した原理によれば、ロックがかかるため、結果は 3 秒後に 1 が出力され、さらに 3 秒後に 1 が出力されます。
スレッド 2 が
public class TestController { public class Task implements Runnable{ private String str; Task(String str){ this.str=str; } @Override public void run() { synchronized (str) { try { Thread.sleep(3000l); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println(str); } } } public static void main(String[] args) throws InterruptedException { TestController testController = new TestController(); Thread thread1 = new Thread(testController.new Task("1")); Thread thread2 = new Thread(testController.new Task("1")); thread1.start(); thread2.start(); } }
に変更された場合、参照オブジェクトの一方は「1」、もう一方は「2」となり、同じオブジェクトではないため、相互にロックされません。排他的で動作しないため、結果は 3 秒後に 1 と 2 がほぼ同時に出力されます。
上記はすべて、同じメソッドを同時に呼び出す複数のスレッドです。異なるメソッドが呼び出された場合はどうなるでしょうか?
Thread thread2 = new Thread(testController.new Task("2"));
上記のコードの出力結果は次のとおりです:
public class Test{ public synchronized void m1(){ System.out.println("m1 running..."); try { Thread.sleep(3000l); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("m1 end"); } public synchronized void m2(){ System.out.println("m2 running..."); System.out.println("m2 end"); } public static void main(String[] args) { Test test = new Test(); new Thread(new Runnable() { @Override public void run() { test.m1(); } }).start(); new Thread(new Runnable() { @Override public void run() { test.m2(); } }).start(); } }
前述のように、同期された変更は synchronized(this){コード ブロックとしてのメソッドのすべてのコード} と同等です。これは、オブジェクトであることを表します。つまり、最初のスレッドがテスト オブジェクトのロックを取得します。オブジェクトはすべて同じテストであるため、2 番目のスレッドはロックを取得できず、ブロックされます。
上記の例を次のように変更します。
m1 running... //过3秒 m1 end m2 running... m2 end
最初のスレッドが m1() を呼び出すと、オブジェクト str のロックが取得され、2 番目のスレッドも m2 を呼び出すときにそれが必要になります。 () オブジェクト str のロックを取得します。これらは同じ Test オブジェクトであるため、2 つの str も同じオブジェクトであるため、2 番目のスレッドはロックを取得できないためブロックされ、出力結果は同じになります。前の例のように。
上記の例を次のように変換すると:
private String str = "1"; public void m1(){ synchronized(str){ System.out.println("m1 running..."); try { Thread.sleep(3000l); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("m1 end"); } } public void m2(){ synchronized(str){ System.out.println("m2 running..."); System.out.println("m2 end"); } }
今回呼び出されるメソッドは 2 つのクラスにありますが、ロックされているため、結果は前の 2 つの例と同じになります。渡されたすべての str オブジェクト。同じオブジェクトのロックは 1 つだけです。最初のスレッドがそれを取得すると、2 番目のスレッドは待機することしかできません。
概要:A. synchronized キーワードがメソッドに追加されるかオブジェクトに追加されるかに関係なく、そのキーワードが作用するオブジェクトが非静的である場合、ロックは取得されるのはオブジェクトです ; 同期されたオブジェクトが静的メソッドまたはクラスの場合、取得されるロックはそのクラス用であり、そのクラスのすべてのオブジェクトは同じロックを持ちます。
B. 各オブジェクトにはロックが 1 つだけ関連付けられており、このロックを取得した人は、そのロックが制御するコードを実行できます。
C. 同期を実現するには多くのシステム オーバーヘッドが必要であり、デッドロックが発生する可能性もあるため、不必要な同期制御は避けるようにしてください。
以上が同期キーワードの使用の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

この記事では、Javaプロジェクト管理、自動化の構築、依存関係の解像度にMavenとGradleを使用して、アプローチと最適化戦略を比較して説明します。

この記事では、MavenやGradleなどのツールを使用して、適切なバージョン化と依存関係管理を使用して、カスタムJavaライブラリ(JARファイル)の作成と使用について説明します。

この記事では、カフェインとグアバキャッシュを使用してJavaでマルチレベルキャッシュを実装してアプリケーションのパフォーマンスを向上させています。セットアップ、統合、パフォーマンスの利点をカバーし、構成と立ち退きポリシー管理Best Pra

この記事では、キャッシュや怠zyなロードなどの高度な機能を備えたオブジェクトリレーショナルマッピングにJPAを使用することについて説明します。潜在的な落とし穴を強調しながら、パフォーマンスを最適化するためのセットアップ、エンティティマッピング、およびベストプラクティスをカバーしています。[159文字]

Javaのクラスロードには、ブートストラップ、拡張機能、およびアプリケーションクラスローダーを備えた階層システムを使用して、クラスの読み込み、リンク、および初期化が含まれます。親の委任モデルは、コアクラスが最初にロードされ、カスタムクラスのLOAに影響を与えることを保証します


ホットAIツール

Undresser.AI Undress
リアルなヌード写真を作成する AI 搭載アプリ

AI Clothes Remover
写真から衣服を削除するオンライン AI ツール。

Undress AI Tool
脱衣画像を無料で

Clothoff.io
AI衣類リムーバー

AI Hentai Generator
AIヘンタイを無料で生成します。

人気の記事

ホットツール

ZendStudio 13.5.1 Mac
強力な PHP 統合開発環境

ゼンドスタジオ 13.0.1
強力な PHP 統合開発環境

EditPlus 中国語クラック版
サイズが小さく、構文の強調表示、コード プロンプト機能はサポートされていません

Safe Exam Browser
Safe Exam Browser は、オンライン試験を安全に受験するための安全なブラウザ環境です。このソフトウェアは、あらゆるコンピュータを安全なワークステーションに変えます。あらゆるユーティリティへのアクセスを制御し、学生が無許可のリソースを使用するのを防ぎます。

ドリームウィーバー CS6
ビジュアル Web 開発ツール
