Object Lock vs Class Lock in Java
Java has two kinds of intrinsic locks. An object lock belongs to one instance: synchronized instance methods and synchronized (this) use it, and it protects that object's instance fields. A class lock belongs to the Class object: static synchronized methods and synchronized (MyClass.class) use it, and it protects static fields. Because they are different locks, a thread holding one doesn't block a thread wanting the other. In this lesson, you will see both locks in action and compare them.
Example: Which Calls Block Each Other?
Let's see an example where pairs of calls are timed. Each method holds its lock for 300 milliseconds; if two calls take about 600 milliseconds together, they blocked each other.
public class Locks {
synchronized void instanceWork() { pause(); }
static synchronized void staticWork() { pause(); }
static void pause() {
try {
Thread.sleep(300);
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
}
}
static String together(Runnable first, Runnable second)
throws InterruptedException {
long start = System.nanoTime();
Thread a = new Thread(first);
Thread b = new Thread(second);
a.start();
b.start();
a.join();
b.join();
long ms = (System.nanoTime() - start) / 1_000_000;
return ms >= 550 ? "waited (one after another)"
: "ran at the same time";
}
public static void main(String[] args) throws InterruptedException {
Locks navika = new Locks();
Locks srihitha = new Locks();
System.out.println("Same object, two instance calls: "
+ together(navika::instanceWork, navika::instanceWork));
System.out.println("Two objects, instance calls: "
+ together(navika::instanceWork, srihitha::instanceWork));
System.out.println("Two static calls: "
+ together(Locks::staticWork, Locks::staticWork));
System.out.println("Static and instance call: "
+ together(Locks::staticWork, navika::instanceWork));
}
}Same object, two instance calls: waited (one after another)
Two objects, instance calls: ran at the same time
Two static calls: waited (one after another)
Static and instance call: ran at the same timeExplanation:
- Two instance calls on the same object share its object lock, so the second waits.
- Instance calls on different objects use different object locks, so they overlap.
- Two static calls share the one class lock, so they wait.
- A static call and an instance call use different locks (class vs object), so they overlap.
Differences Between Object Lock and Class Lock
| Object lock | Class lock | |
|---|---|---|
| Belongs to | One instance | The Class object (one per class) |
| Taken by | synchronized instance methods, synchronized (this) or another object | static synchronized methods, synchronized (X.class) |
| Protects | Instance fields of that object | Static fields |
| How many | One per object | One per class (per class loader) |
| Blocks the other kind | No | No |
Common Mistakes
Thinking a static synchronized method blocks all instance synchronized methods. It doesn't.
Protecting shared static data with object locks. Use the class lock.
Interview Corner
What is the difference between an object lock and a class lock?
An object lock is the intrinsic lock of a particular instance, acquired by synchronized instance methods or synchronized (obj) blocks; it serializes threads using the same object and is used to protect instance state. A class lock is the intrinsic lock of the Class object, acquired by static synchronized methods or synchronized (MyClass.class); there's one per class, and it protects static state. The two are independent, so holding one doesn't block threads acquiring the other.
Practice
- Easy: Predict the result of two
synchronized (Locks.class)blocks run by two threads, then add it to the example to check. - Harder: Add an instance method that locks
Locks.classinstead ofthis, and test whether it blocksstaticWork.
Key Takeaways
Was this tutorial helpful?