[Java] Volatile
1) Volatile
- Used as an indicator to Java Compiler and Thread to not cache value of this variable and always read it from the main memory.
- In multi-threaded environment, threads might cache variables locally. Volatile (or synchronization) ensures the variable is read from main memory.
- Makes variable atomic by implementation.
- Only possible with variables; cannot be used with method or class (illegal operation)
- Guarantees visibility and ordering; write to any volatile variable happens before any read.
- Prevents compiler or JVM form reordering code or moving away them away form synchronization barrier.
2) Example
private boolean bExit;while(!bExit) {checkUserPosition();updateUserPosition();}
- The focus here is the variable, bExit.
- One Thread (Game Thread) can cache the value of bExit instead of getting it form main memory everytime. If in between, any other thread (Event handler thread) changes the value; it would be not be visible to the GameThread.
- Making bExit volatile in Java ensures this will not happen.
3) When to use Volatile?
3.1) Nonatomic 64-bit operations
In Java 64-bit, long and double values are treated as two 32-bit values. This means, a 64-bit write operation is basically performed as two separate 32-bit operations.
When you want to read/write long and double variable atomically, you should use volatile.
3.2) Less overhead version of synchronization
Ensures atomicity of variable without using synchronization (which has more overhead); explained more later.
3.3) Informs Compiler
Inform compiler a variable is subjected to be accessed by multiple threads, which prevents compiler from reordering or making undesired optimizations.
3.4) Double Checked Locking (Singleton Pattern)
4) Important points on Volatile
- Read/Writes are atomic for most reference variable and most primitive variables (except long and double) even without use of volatile keyword.
- Volatile variable don't block, since we are only doing simple read/write.
- Java volatile variable can be null.
- Volatile =/= atomic. For example, volatile++ is not atomic; to make operation atomic, you will need to ensure exclusive access using synchronized method/block in Java.
- If variable is not shared between threads, volatile is not necessary.
5) Synchronized vs Volatile
- Volatile is field modifier while synchronized modifies code blocks and methods.
- Synchronized block, but volatile doesn't; thus, more performance impacting.
- Synchronized have more overhead than volatile, because it synchronizes the value of all variables between thread memory and main memory. Whereas volatile synchronizes only one variable.
Comments
Post a Comment