Topic 5.2
Synchronization and Locks
In one line
synchronized, volatile, Lock, ReentrantLock, ReadWriteLock — the mechanisms, and critically, what each one is (not) for.
Think of it like this
A single-occupancy bathroom key hanging on a hook. Only one person can hold the key (the lock) at a time; everyone else waits outside until it's hung back up.
Key ideas
- 01
synchronized: intrinsic monitor; mutual exclusion + happens-before (both visibility and atomicity for the block).
- 02
volatile: visibility ONLY — no atomicity. Do not use for counters.
- 03
ReentrantLock: explicit lock — tryLock with timeout, lockInterruptibly, fairness option, multiple conditions.
- 04
ReadWriteLock: many readers / one writer — great for read-heavy caches, maps, config stores.
- 05
Deadlock avoidance with locks: always acquire in a consistent global order (or tryLock with timeout).
- 06
Interview one-liner: 'I'd lock the bucket, not the whole registry' — granularity is the craft.
Java / Spring map
- →
java.util.concurrent.locks.ReentrantLock; ReentrantReadWriteLock; StampedLock (optimistic read).
Code & diagrams
volatile vs synchronized vs ReentrantLock in one glance.
class Counter {
private int n = 0;
public synchronized void inc() { n++; } // atomic + visible
}
class VolatileFlag {
private volatile boolean running = true; // visibility of a flag ONLY
public void stop() { running = false; } // safe: single boolean write
public boolean isRunning() { return running; }
}
class LockedCache<K, V> {
private final Map<K, V> map = new HashMap<>();
private final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
public V get(K key) {
lock.readLock().lock(); // many readers together
try { return map.get(key); }
finally { lock.readLock().unlock(); }
}
public void put(K key, V v) {
lock.writeLock().lock(); // exclusive writer
try { map.put(key, v); }
finally { lock.writeLock().unlock(); }
}
}Explain without notes
When is volatile sufficient, and when does the counter version of the same flag corrupt itself?
Practice
Refactor the Parking Lot spot-claim to use a ReadWriteLock instead of synchronized; argue the win.
Trade-offs
- ↔
Locks serialize; the art is shrinking the locked region to the true shared mutation.
Completion checklist
I can state exactly which guarantee (visibility vs atomicity) each mechanism gives.