9

I have multiple methods in a class and most of the methods are having critical sections(shared data). So I made those methods as synchronized. Say thread t1 is running one of the synchronized block . At the same time thread t2 can access the other methods critical section ?

class Sample{

synchronized public void method1(){

}

synchronized public void method2(){

}

synchronized public void method3(){

}

public void method4(){

}

}
Mark Rotteveel
  • 100,966
  • 191
  • 140
  • 197
JavaUser
  • 25,542
  • 46
  • 113
  • 139
  • 2
    the whole object – Maurice Perry Jul 07 '17 at 06:22
  • @JavaUser Assumption : All the thread are created with same Sample Object Answer: If any of the synchronized method (method1 or method2 or method3) is called then all the other Synchronized method will remain blocked till execution is completed . Method 4 will never get block , whatever the situation could be. – MishraJi Jul 07 '17 at 06:30
  • Conversely, if you have two objects of the same type, `Sample s1 = new Sample(); Sample s2 = new Sample();` then when a synchronized method is called on `s1`, only `s1` is locked and not `s2`. That should be obvious but sometimes people forget there's a difference. – markspace Jul 07 '17 at 06:30
  • 1
    A synchronized instance method in Java is synchronized on the instance (object) owning the method. Thus, each instance has its synchronized methods synchronized on a different object: the owning instance. Only one thread can execute inside a synchronized instance method. If more than one instance exist, then one thread at a time can execute inside a synchronized instance method per instance. One thread per instance. see http://tutorials.jenkov.com/java-concurrency/synchronized.html#synchronized-instance-methods – Scary Wombat Jul 07 '17 at 06:32
  • And if `synchronized` method is `static`, then the method owner and that block's monitor is the `Class`, so whole class gets locked. – M. Prokhorov Jul 07 '17 at 06:34
  • Also, if you want the full skinny on Java multithreading, read chapter 17 of the specification. But also get the book ["Java Concurrency in Practice"](http://jcip.net/) by Brian Goetz. It's *the* book for Java multithreading. – markspace Jul 07 '17 at 06:34
  • Please refer https://stackoverflow.com/questions/3047564/java-synchronized-method-lock-on-object-or-method?rq=1, possible dup – sanoj mathew Jul 07 '17 at 06:45

3 Answers3

12

synchronized is always locking on an object. In case of a synchronized method, the object is this. So basically these two methods do the same:

synchronized public void method1() {
  // do something
}

and

public void method1() {
  synchronized(this){
    // do something
  }
}

As long as one thread has the lock on the lock object, no other thread can lock this object. So in your example, the synchronized methods (one, two and three) can never be executed at the same time. method4 is not synchronized, so it can access the object anytime.

If you want a more fine-grained locking, because method1and method2 should be exclusive and method3and method4 you could use for example something like this:

class Sample{
  private final Object lock1 = new Object();
  private final Object lock2 = new Object();

  public void method1(){
    synchronized(lock1) {
      // do something
    }
  }
  public void method2(){
    synchronized(lock1) {
      // do something
    }
  }

  public void method3(){
    synchronized(lock2) {
      // do something
    }
  }
  public void method4(){
    synchronized(lock2) {
      // do something
    }
  }
}

You can then even use the synchonized(lock) method to just wrap the statements that need to be synchronized, not the whole method:

public void method() {
  // some code
  synchronized(lock) {
    // code that must be synchronized
  }
  // some other code
}

With this approach you can keep the lock duration to a minimum.

P.J.Meisch
  • 18,013
  • 6
  • 50
  • 66
  • This is correct, but it should be noted, that in general synchronized should be avoided. It is a brutish method to archive thread-safety and in most cases Concurrent classes are much more suited for the task. – TwoThe Jul 07 '17 at 07:15
  • @TwoThe: I totally agree, I prefer immutable objects, event based and / or stream based architectures etc., but that is a different story. – P.J.Meisch Jul 07 '17 at 07:18
  • 1
    It should probably be also noted that `synchronized static` methods lock on the `Class` object of the class. – Jiri Tousek Jul 07 '17 at 07:22
  • @TwoThe, In what way is `synchronized` brutish? It's simple, it's safe, and it's effective. `java.util.concurrent.locks` provides alternatives that are more powerful, but more power means less safety. If you are talking about other classes in `java.util.concurrent` (e.g., thread-safe queues, maps, etc.) then of course it would be foolish to re-invent those when one of them solves a problem, but they do not solve every problem. – Solomon Slow Jul 07 '17 at 14:27
  • synchronized is also exclusive, which means that it puts all threads on hold to serve only a single one. In many situations that greatly reduces the throughput of applications, in worst cases it turns them back to single-threaded. Those downsides can usually be completely avoided when properly using Concurrent classes. – TwoThe Jul 08 '17 at 06:41
0
  • It is not possible for two invocations of synchronized methods on the same object to interleave. 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.

  • When a synchronized method exits, it automatically establishes a happens-before relationship with any subsequent invocation of a synchronized method for the same object. This guarantees that changes to the state of the object are visible to all threads

gati sahu
  • 2,576
  • 2
  • 10
  • 16
0

In the case

Sample sample1 = new Sample();

Multiple threads can't access

sample1.method1(),sample1.method2(),sample1.method3()

But Multiple threads can access concurrently

sample1.method4()

if we have 2 objects

Sample sample1 = new Sample();
Sample sample2 = new Sample();

Multiple threads can access cocurrently

sample1.method1(),sample2.method1() etc.

so the lock is at object level

jithin joseph
  • 176
  • 1
  • 6