Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Java synchronized method

Consider this code:

public synchronized void onSignalsTimeout(List<SignalSpec> specs) {     if (specs != null && specs.size() > 0) {         for (SignalSpec spec : specs) {             ParsedCANSignal timeoutedSignal = new ParsedCANSignal();             SignalsProvider.getInstance().setSignal(spec.name, spec.parent.parent.channel, timeoutedSignal);         }     } } 

I've got simple question: When Thread 1 calls onSignalsTimeout method, can Thread 2 access objects that are accessed in that method?

Can't find anywhere if 'synchronized' locks only access to this method or access to all objects used in this method.

like image 550
arenaq Avatar asked Jul 27 '15 11:07

arenaq


People also ask

What is synchronized and unsynchronized in Java?

Synchronized access means it is thread-safe. So different threads can access the collection concurrently without any problems, but it is probably a little bit slower depending on what you are doing. Unsynchronized is the opposite. Not thread-safe, but a little bit faster. Follow this answer to receive notifications.

What is synchronized block and synchronized method in Java?

A Synchronized block is a piece of code that can be used to perform synchronization on any specific resource of the method. A Synchronized block is used to lock an object for any shared resource and the scope of a synchronized block is smaller than the synchronized method.

When should a method be synchronized?

Synchronization is needed when Object is mutable. If shared Object is immutable or all the threads which share the same Object are only reading the Object's state not modifying then you don't need to synchronize it. Java programming language provide two synchronization idioms: Methods synchronization.

Which is better synchronized method or block?

Synchronized blocks provide granular control over a lock, as you can use arbitrary any lock to provide mutual exclusion to critical section code. On the other hand, the synchronized method always locks either on the current object represented by this keyword or class level lock, if it's a static synchronized method.


2 Answers

First of all, forget about synchronized methods. A so-called synchronized method...

synchronized AnyType foobar(...) {     doSomething(); } 

Is nothing but a shortcut way of writing this:

AnyType foobar(...) {     synchronized(this) {         doSomething();     } } 

There is nothing special about the method in either case. What is special is the synchronized block, and what a synchronized block does is very simple. When the JVM executes this:

synchronized(foo) {     doSomething(); } 

It first evaluates the expression foo. The result must be an object reference. Then it locks the object, performs the body of the synchronized block, and then it unlocks the object.

But what does locked mean? It may mean less than you think. It does not prevent other threads from using the object. It doesn't prevent them from accessing the object's fields or, from updating its fields. The only thing that locking an object prevents is, it prevents other threads from locking the same object at the same time.

If thread A tries to enter synchronized(foo) {...} while thread B already has foo locked (either in the same synchronized block, or in a different one), then thread A will be forced to wait until thread B releases the lock.


You use synchronized blocks to protect data.

Suppose your program has some collection of objects that can be in different states. Suppose that some states make sense, but there are other states that don't make sense—invalid states.

Suppose that it is not possible for a thread to change the data from one valid state to another valid state without temporarily creating an invalid state.

If you put the code that changes the state in a synchronized(foo) block, and you put every block of code that can see the state into a synchronized block that locks the same object, foo, then you will prevent other threads from seeing the temporary invalid state.

like image 87
Solomon Slow Avatar answered Sep 19 '22 17:09

Solomon Slow


Yes, other threads can access the objects used in the method; the synchronized keyword guarantees that no more than one thread at the time can execute the code of the method.

From https://docs.oracle.com/javase/tutorial/essential/concurrency/syncmeth.html:

  • First, 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.
  • Second, 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. Note that constructors cannot be synchronized — using the synchronized keyword with a constructor is a syntax error. Synchronizing constructors doesn't make sense, because only the thread that creates an object should have access to it while it is being constructed.
like image 26
Andrea Iacono Avatar answered Sep 17 '22 17:09

Andrea Iacono