6

Concurrency in Practiceでは、次の場合に揮発性変数を使用できると書かれています

変数への書き込みは、現在の値に依存しません。

したがって、共有された変更可能な variableaがあり、それに対して行うすべてのスレッドが go である場合a++(それらは値を取得せず、単に++) ます。

引用によると、アトミックでなくてvolatileも作成できるはずですよね?a++

4

4 に答える 4

8

いいえ、変数での使用++volatileスレッドセーフではありません。

a++

次と同等です。

int temp = a;
temp = temp + 1;
a = temp;

そのため、スレッドが読み取ってから別のスレッドが変更された後に への書き戻しaが発生する可能性があるため、が揮発性であっても、スレッドセーフではありませんaa++a

AtomicIntegerスレッドセーフなアトミック インクリメントを実装する を使用できます。

于 2012-11-04T16:56:30.997 に答える
6

a++ は a の値を読み取ります。

  • 読む
  • 読み取り値をインクリメントする
  • 新しい値をに割り当てます

いいえ、この場合、揮発性変数を安全に使用することはできません。

于 2012-11-04T16:57:03.210 に答える
3

- 揮発性は次のことを行います。

  • とマークされたフィールドはvolatile、その値がすぐにメモリに書き込まれ、リタイア中にその値がメモリから読み取られます

  • Threadでの値のキャッシュを防ぎます。

例えば:

a++ 次のように解釈できます。

- aという名前のメモリ位置の値の読み取り。

-値を増やします。

-新たにインクリメントされた値を a という名前のメモリ位置に書き込みます。

上記のプロセス全体がnot スレッドセーフになり++、Java の (インクリメント演算子) はアトミックステートメントではなくなりました。

-キーワードを使用synchronizedすることをお勧めします。使用したくない場合は、AtomicIntegerクラスを使用してください。

于 2012-11-04T17:48:52.397 に答える
1

a++ はアトミックではなく、同等です

  • を取得する
  • 1を追加
  • 結果を

したがって、別のスレッドが邪魔になった場合でも、「更新を見逃す」可能性があります- volatile はそれを防ぐように設計されていません。それが「同期ブロック」と「ロック」の目的です。

a が揮発性であるという事実は、a がローカル キャッシュに格納されていないため、スレッド間での可視性にのみ影響します。そのため、異なるスレッド (異なるコアまたはプロセッサで実行されている) はすぐにその新しい値を「見る」ことができます。

于 2012-11-04T17:43:01.413 に答える