22
class A {
    public synchronized void myOneMethod() {
        // ...
    }
}

class B extends A {
    public synchronized void myOtherMethod() {
        // ...
    }
}

// ...

B myObject;

// ...

myObject.myOneMethod(); // acquires lock
myObject.myOtherMethod(); // same lock?

How I understand the synchronization model, I'd say that yes, it does, because the lock / monitor is associated with the instance myObject, and it doesn't matter where the method was defined. But am I right? If not, why? If yes, why are you sure, and I'm not? :-)

Hanno Fietz
  • 30,799
  • 47
  • 148
  • 234

7 Answers7

15

Yes, you are right, and you got the explanation right too. Nothing much to add.

Note that if the methods were static, then they would synchronize on different objects, namely their respective classes (A and B).

EDIT: Why am I sure? I don't know, why are you not sure? ;-) myObject is just one object - there isn't any distinction between the myObject attributes that come from class A and those that come from class B. (Well, technically you could probably use reflection to find out which are which, so there must be some distinction, but forget about reflection for now. For common operations on the object there's no distinction.)

David Z
  • 128,184
  • 27
  • 255
  • 279
8

Yes, synchronized is equivalent to synchronized(this).

To be more precise:

For a class (static) method, the lock associated with the Class object for the method's class is used. For an instance method, the lock associated with this (the object for which the method was invoked) is used.

pgras
  • 12,614
  • 4
  • 38
  • 46
3

If you want to be more explicit about your locking, you could do something like this:

class A {

    protected final Object  mutex = new Object();
    public void myOneMethod() {
        synchronized (mutex) {
            // ...
        }
    }
}

class B extends A {
    public  void myOtherMethod() {
        synchronized (mutex) {
            // ...
        }
    }
}

In fact, this pattern is recommended by Brian Goetz in Java Concurrency in Practice, section 4.2.1 "The Java monitor pattern". That way you know exactly where your monitor is coming from.

Julien Chastang
  • 17,592
  • 12
  • 63
  • 89
  • Yup. Also, this is what Jon Skeet does: http://stackoverflow.com/questions/609963/java-what-if-anything-is-locked-by-synchronized-methods-apart-from-the-object/609981#609981 ;) I'll use that pattern, except for those methods where it actually makes most sense to lock on "this". – Hanno Fietz Mar 09 '09 at 20:07
  • Thank you for mentioning this approach. Still, the original Q may refer to a class A coming from a library. At least, that's why I searched for the topic. In that case, it seems that additional considerations come into play. – class stacker Apr 15 '15 at 06:01
1

Yes. Java uses "monitors" to implement synchronization, and synchronized methods use the object instance they're called on as monitor, which is obviously the same in this case.

Note that this is NOT true for static methods! There, the class instance of (I think) the declaring class is used, which would not be the same one.

Michael Borgwardt
  • 342,105
  • 78
  • 482
  • 720
0

From the conceptual viewpoint, the mutex integrity of some inheritance scenarios would be broken if synchonized methods of class A would only protect A's data in the context of subclass B. After all, not all of A's data is required to be private.

Imagine that you want to slightly extend the functionality of one method of A while keeping the rest of A's functionality including mutex protection. If A were only protecting itself, you would end up having to override all of A's synchronized methods to lift the original synchronization mechanism to the new subclass. Not very attractive and also not very efficient.

class stacker
  • 5,357
  • 2
  • 32
  • 65
0

Just a small addition for people who might be interested in the future..

Additionally remember that locks in Java are reentrant. If they were not this code of yours would result in a deadlock since as you've indicated both operations require the same lock.

Selim
  • 1,013
  • 9
  • 15
0

Yes you are correct

When one thread is executing a synchronized method for an object, all other threads that invoke synchronized methods for the same object block (suspend execution) until the first thread is done with the object. In this case the object is B

Paul Whelan
  • 16,574
  • 12
  • 50
  • 83