Java Concurrency In Practiceで用語が定義されているように、クラスは「事実上不変」です。
これは、インスタンスへの参照が「安全に公開」されている限り、それらは不変であることを意味します。参照を安全に公開するには、同期を使用して、Java メモリ モデル (JMM) が、呼び出し元が完全に書き込まれたフィールドの値を確認できることを保証できるようにする必要があります。たとえば、フィールドが final ではなく、インスタンスが構築されて別のスレッドに渡された場合、他のスレッドはそのフィールドを未定義の状態 (null
オブジェクト参照であるか、64 ビットlong
フィールドの半分のみであるかなど) で見る可能性があります。 )。
インスタンスが単一のスレッドでのみ使用される場合、区別は問題になりません。これは、JMM が「スレッド内 as-if-serial」セマンティクスを使用するためです。したがって、コンストラクター内でのフィールドの割り当ては、フィールドが読み取られる前に常に行われます。
フィールドが の場合final
、JMM は、参照がどのように公開されても、呼び出し元が正しい値を表示することを保証します。したがってfinal
、同期の形式を使用せずにインスタンスを他のスレッドに渡したい場合に役立ちます。