7

重複の可能性:
コンストラクターの競合状態をシミュレートする方法は?
適切に公開されていない値に関する競合状態を示す方法は?

《実際の Java 同時実行》から次のコードを取得しました。

public class Holder{

  private int n;
  public Holder(int n){this.n = n;}
  public void assertSanity(){
     if(n != n) throw new AssertionError("This statement is false.");

  }


}

条件が気にn != nなりますが、これは特定の状況下で当てはまるのでしょうか?</p>

4

5 に答える 5

2

私の推測では、あなたは次のような質問をしていると思います:

この本は、オブジェクトが完全に構築される前にオブジェクトへの参照を共有する可能性について話していると思います。言及されている行為は不適切な公開です。

n != n次のステップに分割されているとします。

Access n on the right side of the operand
Access n on the left side of the operand
Compare values

nしたがって、最初の 2 つのステップの間で の値が変化するケースは想像に難くありません。「でも変わらない」という気持ちはよくわかりますn。実際には、Holderそのインスタンスのコンストラクターが完全に実行される前に、2 つのスレッドが のインスタンスへのアクセスを共有できるためです。

于 2012-09-24T05:51:14.063 に答える
0

おそらく、コンパイラはこれを常に false として最適化しますが、そうでない場合、マルチスレッド環境では true を返す可能性があります。

左の n が aa レジスターにコピーされたとします。次に、現在のスレッドが中断され、次のスレッドが n を変更してから、最初のスレッドに戻ります。ここで、右辺 n がレジスタにコピーされ、(2 つのレジスタに対する) 比較操作が呼び出されます。

この場合、それらは異なります。

編集: 以下の nhantdh のコメントのバイトコードを見ると、n に対して 2 つのロードが実行されていることがわかります。したがって、2 つの間の変更による割り込みにより、式が true に評価される可能性があります。

于 2012-09-24T05:43:32.027 に答える
0

nではないので、理論的には可能だと思いvolatileます。つまり、スレッドはHolderオブジェクトを構築できますが、設定された値nは、比較操作を呼び出す別のコアで実行されている別のスレッドには表示されません。

于 2012-09-24T05:57:07.630 に答える
0

値は常に同じになります。

変数がプリミティブ型であり、変数が非静的であり、セッターがない限り、必要な数のクラス インスタンスを作成できます。インスタンスは、変数「n」で同じ「オブジェクト」/インスタンスを共有することはありません。

コンストラクターの再呼び出し後に値を変更すると、セッターやリフレクションのように値が異なる場合があります。

于 2012-09-24T06:57:15.363 に答える
-2

この式は C++ で知っています。nが数値でない場合は true です。C++ で double (または float) が NaN であるかどうかの確認を参照してください。

于 2012-09-24T05:43:34.823 に答える