Skip to content

Java Locks ​

🧩 1. What Is a "Lock"? ​

A lock is a mechanism in multithreaded concurrent programming used to control access to shared resources.

Core goal: Prevent multiple threads from modifying the same data simultaneously, which could cause data inconsistency (thread-safety issues).


🎯 Real-world Analogy ​

Imagine you and others share a folder (a shared resource):

  • Without a lock: you both edit a file at the same time β†’ the file gets corrupted
  • With a lock: when one person edits, others must wait

That’s the intuitive idea behind a β€œlock.”


βš™οΈ 2. Types of Locks in Java ​

Java provides multiple locking mechanismsβ€”from language-level features to library-level APIs:

LevelMechanismDescription
Syntax levelsynchronizedThe most common keyword (implicit lock)
API leveljava.util.concurrent.locks.LockExplicit lock (e.g., ReentrantLock)
Atomic classesjava.util.concurrent.atomic.*Lock-free (CAS-based optimistic lock)

Let’s explore them one by one πŸ‘‡


🧱 1️⃣ synchronized β€” The Intrinsic (Monitor) Lock ​

synchronized is the classic synchronization mechanism. Simple usage:

java
synchronized (obj) {
    // critical section
}

It relies on a Monitor lock inside the object header, which is a type of pessimistic lock (explained later).

You can also use it on methods:

java
public synchronized void add() { ... }

At the bytecode level, the compiler generates monitorenter and monitorexit instructions.


βš™οΈ 2️⃣ Lock Interface and Implementations (Explicit Locks) ​

Introduced in JDK 1.5: java.util.concurrent.locks.Lock. It provides more flexibility than synchronized:

java
Lock lock = new ReentrantLock();
lock.lock();
try {
    // critical section
} finally {
    lock.unlock();
}

Advantages:

  • Can attempt to acquire a lock (tryLock())
  • Can acquire interruptibly (lockInterruptibly())
  • Supports fair and unfair locking

Lock implementations are usually built on top of AQS (AbstractQueuedSynchronizer).


πŸ’‘ 3️⃣ CAS (Compare-And-Swap) and Atomic Classes ​

CAS is a lock-free mechanism, based on optimistic locking.

Example:

java
AtomicInteger i = new AtomicInteger(0);
i.incrementAndGet(); // internally uses CAS

CAS is a hardware-level atomic instruction: It compares a current value in memory with an expected value, and updates only if they match; otherwise, it retries.


🧠 3. Lock Classifications (Important!) ​

When discussing Java locks, you’ll often hear about:

Pessimistic vs Optimistic Locks Fair vs Unfair Locks Reentrant vs Non-reentrant Locks Read/Write Locks Spin Locks

Let’s clarify them πŸ‘‡


πŸ”’ 1️⃣ Pessimistic Lock ​

  • Assumes conflicts are likely, so it locks first, then operates.
  • Typical examples: synchronized, ReentrantLock

Example:

java
synchronized (this) {
    count++;
}

Other threads must wait for the lock to be released. Safe but potentially slow.


😊 2️⃣ Optimistic Lock ​

  • Assumes conflicts are rare, so it operates first, then checks.
  • If a conflict occurs, it retries.

Implemented via CAS (Compare-And-Swap)

Simplified example:

java
while (true) {
    int oldValue = atomicInt.get();
    int newValue = oldValue + 1;
    if (atomicInt.compareAndSet(oldValue, newValue)) {
        break; // success
    }
    // otherwise retry
}

βœ… Advantages: High performance (no blocking) ⚠️ Drawback: Under high contention, frequent retries can waste CPU cycles.


🧭 3️⃣ Fair vs Unfair Locks ​

  • Fair lock: Threads acquire the lock in the order they requested it.
  • Unfair lock: Threads can β€œjump the queue,” improving throughput.

ReentrantLock defaults to unfair, but you can specify:

java
new ReentrantLock(true); // fair lock

πŸ” 4️⃣ Reentrant Lock ​

A lock is reentrant if the same thread can acquire it multiple times without deadlocking.

Example:

java
public synchronized void a() {
    b(); // re-enters the same lock
}
public synchronized void b() { }

Both synchronized and ReentrantLock are reentrant.


πŸ“š 5️⃣ Read/Write Lock ​

When reads greatly outnumber writes, ReadWriteLock improves concurrency:

  • Multiple threads can read simultaneously
  • Writes are exclusive

Example:

java
ReadWriteLock rwLock = new ReentrantReadWriteLock();
rwLock.readLock().lock();
...
rwLock.writeLock().lock();

πŸ” 6️⃣ Spin Lock ​

A spin lock doesn’t suspend a thread while waiting for a lock. Instead, it loops repeatedly checking if the lock is available.

This can reduce context switching overhead under low contention.

Java’s CAS operations embody this β€œspinning” concept.


πŸ“Š 4. Relationship and Evolution of Locks (Summary Diagram) ​

Lock hierarchy:
β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”
β”‚ synchronized (pessimistic, intrinsic) β”‚
β”‚ ReentrantLock (explicit, reentrant)   β”‚
β”‚ ReadWriteLock (fine-grained)          β”‚
β”‚                                       β”‚
β”‚ β†’ AQS (underlying framework)          β”‚
β”‚ β†’ CAS (hardware-level instruction)    β”‚
β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜
         ↑
         └─ Optimistic Locking (CAS-based)

⚑ 5. One-Line Summary Table ​

TypeDescriptionTypical Implementations
PessimisticLocks first, prevents conflictssynchronized, ReentrantLock
OptimisticOperate first, check & retryAtomicInteger, CAS
FairFIFO lock acquisitionReentrantLock(true)
UnfairAllows lock jumpingReentrantLock(false)
ReentrantSame thread can re-locksynchronized, ReentrantLock
Read/WriteRead shared, write exclusiveReentrantReadWriteLock

Just something casual. Hope you like it. Built with VitePress