質問には2つの質問があるため、質問には2つの部分で答えることができます。
1)アトミック変数に関するOracleのチュートリアルドキュメントを参照してください:
https ://docs.oracle.com/javase/tutorial/essential/concurrency/atomicvars.html
java.util.concurrent.atomicパッケージは、単一変数に対するアトミック操作をサポートするクラスを定義します。すべてのクラスには、揮発性変数の読み取りと書き込みのように機能するgetメソッドとsetメソッドがあります。つまり、セットには、同じ変数に対する後続のgetとの発生前の関係があります。アトミックcompareAndSetメソッドには、整数アトミック変数に適用される単純なアトミック算術メソッドと同様に、これらのメモリ整合性機能もあります。
したがって、ここで他の回答が述べているように、アトミック整数は内部で揮発性を使用します。したがって、アトミック整数を揮発性にすることには意味がありません。メソッドを同期する必要があります。
Udemyに関するJohnPurcellの無料ビデオをご覧ください。ここでは、複数のスレッドが変更しようとしているときにvolatileキーワードが失敗することを示しています。シンプルで美しい例。
https://www.udemy.com/course/java-multithreading/learn/lecture/108950#overview
Johnの例の揮発性カウンターをアトミック変数に変更すると、彼のチュートリアルで行ったように、sunchronizedキーワードを使用せずに彼のコードが成功することが保証されます。
2) Coming to your code :
Say thread 1 kicks into action and "someMethod" does a get and checks for size. It is possible that before getAndIncrement executes(say, by thread 1) , another thread (say thread 2)kicks in and increases the count to 10, and gets out; after which, your thread 1 will resume and increase count to 11. This is erroneous output. This is because your "someMethod" is not protected in anyway from synhronization problems.
I would still recommend you to watch john purcell's videos to see where volatile fails , so that you have a better understanding of the keyword volatile. Replace it with atomicinteger in his example and see the magic.