3
class ThreadSafe implements Runnable {
  int arr[]=new int[]{1,2,3,4,5};
  int sum=0;
  public void run() {
    int result=sum();
    System.out.println("for "+Thread.currentThread().getName()+"the value        is"+result);
  }

  public int sum() {
    for(int i=0;i<5;i++) {
      sum=sum+arr[i];
      System.out.println("calculating sum for      thread"+Thread.currentThread().getName()+"sum ="+sum);
      try {
        Thread.sleep(10);
      } catch(Exception e) {}
    }
    return sum;
  }

  public static void main(String...d) {
    ThreadSafe ts=new ThreadSafe();
    ThreadSafe ts1=new ThreadSafe();
    Thread t=new Thread(ts);
    Thread t1=new Thread(ts1);
    t1.start();
    t.start();
  }
}

合計メソッドが同期されていないため、複数のスレッドが同時に合計メソッドを実行できるため、出力が15にならないことを期待していました。

2つのスレッドがsumメソッドを即座に実行するため、最初のスレッドがsumの値を別のスレッドによって読み取られる値に更新するため、出力が15になることはないはずです。

だから私の質問は、sum()メソッドを同期していないのに、なぜプログラムの出力が期待どおりに出力されるのかということです。

4

2 に答える 2

7

ThreadSafeそれぞれが独自のsumインスタンス変数を持つ、の2つのインスタンスを作成しています。

それらを互いに上書きしたい場合(これはただ遊んでいると思います)、Threadの同じインスタンスに2つのを作成しますThreadSafe。また、sum変数をvolatileとしてマークして、別のスレッドで変更できることを示します(コンパイラがメソッド内の他の場所で変更されていないことを検出した場合に、値の内部キャッシュを回避するため)。

たとえば、mainメソッドを次のように変更します。

public static void main(String...d) {
    ThreadSafe ts=new ThreadSafe();
    Thread t=new Thread(ts);
    Thread t1=new Thread(ts);
    t1.start();
    t.start();
  }

そしてThreadSafeこれに対するあなたのクラス定義の始まり:

class ThreadSafe implements Runnable {
  int arr[]=new int[]{1,2,3,4,5};
  volatile int sum=0;
于 2012-08-27T13:19:04.760 に答える
0

ThreadSafe異なるスレッドによって処理される2つのインスタンスがあるためです。目的の結果を生成するには、1つのインスタンスと複数のスレッドが同じインスタンスで動作しているようなものである必要があります

于 2012-08-27T13:20:53.250 に答える