この記事では、同期の詳細な説明の4つの例を共有しています
1.同期されたキーワードを追加するかどうか
public class threadtest {public static void main(string [] args){example example = new Example();スレッドT1 = new Thread1(例);スレッドT2 = new Thread1(例); t1.start(); t2.start(); }} class example {public synchronized void exaur(){for(int i = 0; i <5; ++ i){try {thread.sleep(1000); } catch(arturnedexception e){e.printstacktrace(); } system.out.println( "excute:" + i); }}} class thread1 extends thread {private example example; public thread1(例の例){this.example = example; } @Override public void run(){example.excute(); }}同期されたキーワードの出力結果は次のとおりです
最初に0-4のセットが出力され、次に次のセットが出力され、2つのスレッドが順番に実行されます。
エクスパート:0
エクスクトル:1
エクスパート:2
エクスパート:3
エクスパート:4
エクスパート:0
エクスクトル:1
エクスパート:2
エクスパート:3
エクスパート:4
同期されたキーワードの出力結果は次のとおりです
2つのスレッドは、エクスパートメソッドを同時に同時に実行します
エクスパート:0
エクスパート:0
エクスクトル:1
エクスクトル:1
エクスパート:2
エクスパート:2
エクスパート:3
エクスパート:3
エクスパート:4
エクスパート:4
2。複数の方法のマルチスレッド状況
public class threadtest {public static void main(string [] args){example example = new Example();スレッドT1 = new Thread1(例);スレッドT2 = new Thread2(例); t1.start(); t2.start(); }} class example {public synchronized void exaur(){for(int i = 0; i <5; ++ i){try {thread.sleep(1000); } catch(arturnedexception e){e.printstacktrace(); } system.out.println( "excute:" + i); }} public synchronized void exaur1(){for(int i = 0; i <5; ++ i){try {thread.sleep(1000); } catch(arturnedexception e){e.printstacktrace(); } system.out.println( "excute1:" + i); }}} class thread1 extends thread {private example example; public thread1(例の例){this.example = example; } @Override public void run(){example.excute(); }} class thread2拡張スレッド{private Exampleの例; public thread2(例の例){this.example = example; } @Override public void run(){example.excute1(); }}実行結果は次のとおりです
同じことが順番に実行され、別のスレッドが実行される前に1つのスレッドが実行されます。
エクスパート:0
エクスクトル:1
エクスパート:2
エクスパート:3
エクスパート:4
excute1:0
excute1:1
excute1:2
excute1:3
排他1:4
同期されたキーワードが削除された場合、2つの方法は同時に実行され、相互の影響力はありません。
しかし、例の例で書かれているように、2つの方法でさえ:
実行結果は、常に1つのスレッドの出力と、別のスレッドの実行です。
説明:
オブジェクトに複数の同期メソッドがあり、スレッドが特定の瞬間に同期されたメソッドを入力した場合、他のスレッドはメソッドを実行する前にオブジェクトの同期メソッドにアクセスできません。
結論は:
同期されたキーワードがメソッドを変更すると、メソッドは同期メソッドと呼ばれます。
Javaの各オブジェクトには、ロックまたはモニターがあります。スレッドがオブジェクトの同期されたメソッドにアクセスすると、オブジェクトはロックされ、他のスレッドはオブジェクトの同期メソッドにアクセスできません(ここでは、同じ方法だけでなく、すべての同期メソッドを指します)。前のスレッドが実行方法を完了する(または例外をスローする)、オブジェクトのロックがリリースされるまで、他のスレッドがオブジェクトの同期メソッドに再びアクセスできるようにすることではありません。
この時点でオブジェクトがロックされていることに注意してください。別のオブジェクトの場合、オブジェクト間に制限関係はありません。
コード内の2番目のスレッドオブジェクトを作成しようとすると、新しい例オブジェクトが渡されます。その後、2つのスレッドの実行間に制限はありません。
3。静的同期方法
同期されたキーワード修正メソッドも静的によって変更されると、非静的同期メソッドがオブジェクトをロックすることが以前に言われていますが、静的メソッドはオブジェクトではなくクラスに属し、このメソッドが配置されているクラスのクラスオブジェクトをロックします。
public class threadtest {public static void main(string [] args){example example = new Example();例example2 = new Example();スレッドT1 = new Thread1(例);スレッドT2 = new Thread2(Example2); t1.start(); t2.start(); }} class example {public synchronized static void exaur(){for(int i = 0; i <5; ++ i){try {thread.sleep(1000); } catch(arturnedexception e){e.printstacktrace(); } system.out.println( "excute:" + i); }} public synchronized static void exaur1(){for(int i = 0; i <5; ++ i){try {thread.sleep(1000); } catch(arturnedexception e){e.printstacktrace(); } system.out.println( "excute1:" + i); }}} class thread1 extends thread {private example example; public thread1(例の例){this.example = example; } @Override public void run(){example.excute(); }} class thread2拡張スレッド{private Exampleの例; public thread2(例の例){this.example = example; } @Override public void run(){example.excute1(); }}実行結果は次のとおりです
エクスパート:0
エクスクトル:1
エクスパート:2
エクスパート:3
エクスパート:4
excute1:0
excute1:1
excute1:2
excute1:3
排他1:4
静的修飾子がなく、2つのスレッドが異なるオブジェクトを渡す場合、それらは同時に同時に実行されます。
したがって、静的メソッド(execute()とexecute2()の両方が静的キーワードが追加されている場合)である場合、異なるサンプルオブジェクトが2つのスレッドに渡されたとしても、2つのスレッドは互いに制限されています。最初に実行し、次に次に実行する必要があります。
結論は:
同期されたメソッドが静的である場合、スレッドがメソッドにアクセスすると、同期されたメソッドが配置されているオブジェクトではなく、同期されたメソッドが配置されているクラスに対応するクラスオブジェクトをロックします。 Javaでは、クラスにいくつのオブジェクトがある場合でも、これらのオブジェクトは一意のクラスオブジェクトに対応します。したがって、スレッドが同じクラスの2つのオブジェクトの2つの静的および同期メソッドにアクセスすると、実行順序もシーケンシャルになります。つまり、1つのスレッドがメソッドを最初に実行し、もう1つのスレッドは実行が完了した後に開始します。
4。同期ブロック
同期(オブジェクト)
{
}
これは、スレッドが実行されるとオブジェクトをロックすることを意味します。 (このオブジェクトは、任意のクラスのオブジェクトであるか、このキーワードを使用できます)。
これにより、ロックされたオブジェクトを自分で指定できます。
public class threadtest {public static void main(string [] args){example example = new Example();スレッドT1 = new Thread1(例);スレッドT2 = new Thread2(例); t1.start(); t2.start(); }} class example {public void exaur(){synchronized(this){for(int i = 0; i <5; ++ i){try {thread.sleep(1000); } catch(arturnedexception e){e.printstacktrace(); } system.out.println( "excute:" + i); }}} public void exhaut1(){synchronized(this){for(int i = 0; i <5; ++ i){try {thread.sleep(1000); } catch(arturnedexception e){e.printstacktrace(); } system.out.println( "excute1:" + i); }}}}}} classスレッド1拡張スレッド{private例の例; public thread1(例の例){this.example = example; } @Override public void run(){example.excute(); }} class thread2拡張スレッド{private Exampleの例; public thread2(例の例){this.example = example; } @Override public void run(){example.excute1(); }}実行結果は次のとおりです
エクスパート:0
エクスクトル:1
エクスパート:2
エクスパート:3
エクスパート:4
excute1:0
excute1:1
excute1:2
excute1:3
排他1:4
プログラム4の例で達成される効果は、プログラム2の例と同じです。両方のスレッドは、同時にではなく、順番に実行されます。 1つのスレッドが実行されると、オブジェクトオブジェクトがロックされ、もう1つのスレッドが対応するブロックを実行できません。
同期された方法は、実際には、メソッドのすべてのステートメントを同期したブロックでラッピングし、同期ブロックのブラケットにこのキーワードを渡すことと同等です。もちろん、静的な方法の場合、クラスオブジェクトをロックする必要があります。
おそらく、メソッドのコードの数行のみがスレッドの同期の問題を伴うため、同期されたブロックは、同期されたメソッドよりも詳細に複数のスレッドのアクセスを制御します。同期ブロック内のコンテンツのみが同時に複数のスレッドでアクセスできず、メソッドの他のステートメントは、同時に(同期ブロックの前後を含む)複数のスレッドでアクセスできます。
結論は:
同期された方法は、粗粒の並行制御です。特定の瞬間に、同期されたメソッドを実行できるスレッドは1つだけです。
同期されたブロックは、ブロック内のコードのみを同期する微調整された並行性制御です。メソッドおよび同期ブロック以外にある他のコードは、複数のスレッドで同時にアクセスできます。
上記は、Javaマルチスレッドプログラミングの同期ブロック同期方法に関するものです。みんなの学習に役立つことを願っています。