の使用ので、私はキーワードでテストしていました。ここに私が試した例です。学習Java、同期キーワード
public class MyTest {
static int i = 0;
public static void main(String[] args) {
new Thread(t1).start();
new Thread(t2).start();
}
private static void countMe(String name){
i++;
System.out.println("Current Counter is: " + i + ", updated by: " + name);
}
private static Runnable t1 = new Runnable() {
public void run() {
try{
for(int i=0; i<5; i++){
countMe("t1");
}
} catch (Exception e){}
}
};
private static Runnable t2 = new Runnable() {
public void run() {
try{
for(int i=0; i<5; i++){
countMe("t2");
}
} catch (Exception e){}
}
};
}
私はそれを実行すると、二つのスレッドからcountMe()
メソッドを呼び出すの出力は、この出力を生成します。
Current Counter is: 1
Current Counter is: 2
Current Counter is: 4
Current Counter is: 5
Current Counter is: 6
Current Counter is: 7
Current Counter is: 3
Current Counter is: 8
Current Counter is: 9
Current Counter is: 10
そして私は方法countMe()
を変更します。
private synchronized static void countMe(){
i++;
System.out.println("Current Counter is: " + i);
}
私はこの出力を得る:
Current Counter is: 1
Current Counter is: 2
Current Counter is: 3
Current Counter is: 4
Current Counter is: 5
Current Counter is: 6
Current Counter is: 7
Current Counter is: 8
Current Counter is: 9
Current Counter is: 10
これは私にの目的を明確に理解してくれますが、他にも理由があることを知りたいので、を使用することができます。または私がここでやったことは、なぜこのキーワードを使う必要があるのか?
ありがとうございました。
EDIT:私が混乱しているもう一つの点は、カウンタが7の後に3になった理由です。私には不可能なようですが、試してみると同じような結果が起こります。 ?
スレッドが交代する保証はありません。他のスレッドが7にカウントされるまで、3を数えたスレッドが印刷されないことがあります。 –
ありがとうございます。しかし、7より後で次の呼び出しを印刷することはできますか?3、6または5を印刷できます。それが3だった後に私は読んでいない、これは非常に奇妙に聞こえる。だから、私は2つ以上のスレッドから同じコードブロックを使用する必要があるたびに常に同期を使用することが賢明でなければならないと思いますか? – 911TurboS
スレッドの名前を印刷することをお勧めします。混乱がどこにあるのかがより明らかになります。並行処理は複雑なトピックであり、単純な答えはありません。私の好みは、アクターのパターンを使用し、可能な限りスレッド間でデータをほとんど共有しないことです。理想的には、なし。非常に効率的にコードを実行する1つのスレッドは、通常は十分です。 –