aspose file tools*
The moose likes Threads and Synchronization and the fly likes Synchronized method/blocks.....??????? Big Moose Saloon
  Search | Java FAQ | Recent Topics | Flagged Topics | Hot Topics | Zero Replies
Register / Login
JavaRanch » Java Forums » Java » Threads and Synchronization
Bookmark "Synchronized method/blocks.....???????" Watch "Synchronized method/blocks.....???????" New topic
Author

Synchronized method/blocks.....???????

anand rk
Greenhorn

Joined: Feb 07, 2001
Posts: 25
Hello,
Can anyone explain to me the difference between Synchronized methods and Synchronized blocks.May be with an example
I am not able to get it
Anand
Dean J
Greenhorn

Joined: Jan 28, 2001
Posts: 7
Synchronization makes sure that we donot write in a common memory space by more than one thread.
Sync. methods are used when you think that the entire method should be locked from access to the other thread.
Sync. blocks are used when you know that the rest of the method is Ok to be left un-sync'ed, but only a portion of the code need to be taken care of. Usually, this is done by calling
public void run()
{
// code
// code
// sync only this piece of code
synchronized(this)
{
// block of code that needs to be sync'ed
}
// code
}
Hope this helps
D.J
Rahul Rathore
Ranch Hand

Joined: Sep 30, 2000
Posts: 324
These 2 methods are equivalent:-
public synchronized void method() {
//code
}
public void method() {
synchronized(this) {
//code
}
So the first form is simply a short-hand way of forcing the calling thread to acquire a lock on 'this' object, before it executing the method code. The lock is acquired at the start of the method execution and is released when the thread returns from the method.
But the second form is more flexible- because it permits 2 variations:-
1. A synchronized block can be a part of the method code-
public void method() {
//some code-A
synchronized(this) {
//some code-B
}//end of synchronized block
//some code-C
}//end of method
The thread executing this method can execute code-A without a lock but must acquire a lock on 'this' object when it attempts to execute code-B. The lock is released after executing code-B. So code-C is executed without any lock. This minimizes the amount of time a lock is retained by keeping it only where necessary.
2. The second variation possible when we use synchronized block is that we can specify synchronization on any arbitrary object (not only 'this' object). This synchronized(someObject){//code} would force the executing thread to acquire a lock on someObject.
Mark Savory
Ranch Hand

Joined: Feb 08, 2001
Posts: 122
Here's an example of a class with a method that adds unique values to a hashtable:
public class Test {
Hashtable table = new Hashtable();
public void add(String name, String value) {
synchronized (table) {
if (table.get(name) == null)
table.put(name, value);
}
}
public void somethingelse() {
// Code...
}
}
Suppose that we had two threads accessing the same Test object. One thread could call 'add' while the other thread symultaneously calls 'somethingelse' because the lock is on 'table' rather than this(Test object). This would not be true if the 'add' method itself was defined as synchronized.
[This message has been edited by Mark Savory (edited March 02, 2001).]
Rahul Rathore
Ranch Hand

Joined: Sep 30, 2000
Posts: 324
Mark
Even if add() method was defined as 'synchronized' another thread CAN concurrently access somethingelse() because somethingelse() is NOT defined as synchronized. A thread executing somethingelse() will NOT be required to acquire any lock. Therefore such thread will NOT be affected by the fact that another thread has acquired a lock, on this object.
Concurrent access will be precluded only if somethingelse() is also defined as synchronized.
More generally 2 threads cannot execute concurrently if BOTH are forced to acquire a lock/monitor on the SAME object, whether such object is 'this' or any other object.
Jim Baiter
Ranch Hand

Joined: Jan 05, 2001
Posts: 532
One thing to watch for with this code is that you aren't
really preventing other methods from accessing the Hashtable.
The synchronization protocol only says that at most one thread at any time can be in that critical section (sync block). Another method could modify that Hashtable simultaneously with the add method. This can be a definite advantage in using a synchronized container.
Originally posted by Mark Savory:
...
public class Test {
Hashtable table = new Hashtable();
public void add(String name, String value) {
synchronized (table) {
if (table.get(name) == null)
table.put(name, value);
}
}
public void somethingelse() {
// Code...
}
}
[This message has been edited by Mark Savory (edited March 02, 2001).][/B]

[This message has been edited by Jim Baiter (edited March 03, 2001).]
[This message has been edited by Jim Baiter (edited March 03, 2001).]
Mark Savory
Ranch Hand

Joined: Feb 08, 2001
Posts: 122
Rahul,
Thanks for correcting me on my last reply.
My point would be valid if I just made 'somethingelse' sychronized. In that case, a thread calling 'somethingelse' could acquire a lock on the Test object while symultaneously a second thread could acquire a lock on the hashtable when in the critical block of the 'add' method'.
Mark Savory
Ranch Hand

Joined: Feb 08, 2001
Posts: 122
Jim,
Could you please clarify what you mean by 'sychronized container'. Before you do, let me say that I would make the hashtable private(I meant to do this in the first place). Also, If I was going to add new methods that access the hashtable, I would synchronize that critical code on the hashtable object.
Jim Baiter
Ranch Hand

Joined: Jan 05, 2001
Posts: 532
Ok, that's fine - it was misworded on my part - sorry.
Peter den Haan
author
Ranch Hand

Joined: Apr 20, 2000
Posts: 3252
As an aside...
If you're going to make the Hashtable private and synchronize all access to it, replace it by a HashMap. A HashMap is more efficient than a Hashtable because it is not synchronized. It also fits better with the rest of the Java 1.2 Collection framework (no surprise because it's part of it).
(Personally I'd use a HashMap regardless, and use Collections.synchronizedMap() on it if necessary, but maybe I'm a Collection zealot).
- Peter
Mark Savory
Ranch Hand

Joined: Feb 08, 2001
Posts: 122
Peter,
Your right. The method Hashtable.put is already synchronized, so I needn't access it from a synchronized block. I was wondering if someone would point that out.
About HashMap, maybe you can clear something up for me. Suppose I choose to use HashMap rather than Hashtable because it fits better into the Collection framework. What is the purpose of calling Collections.synchronizedMap()? The javadoc for the Collections has this example code:
Map m = Collections.synchronizedMap(new HashMap());
...
Set s = m.keySet(); // Needn't be in synchronized block
...
synchronized(m) { // Synchronizing on m, not s!
Iterator i = s.iterator(); // Must be in synchronized block
while (i.hasNext())
foo(i.next());
}
Why "Map m = Collections.synchronizedMap(new HashMap())" instead of Map m = new HashMap()?
Rahul Rathore
Ranch Hand

Joined: Sep 30, 2000
Posts: 324
Without Collections.synchronizedMap() (assuming there is no external synchronization) the behaviour will be non-deterministic.
1. The use of the above method ensures that any thread trying to execute a method of Map will be forced to aquire lock on the Map.
2. But the above method does NOT make access through ITERATORS synchronized. So if we are accessing through iterators, such access must be separately synchronized on the Map.
Consider what may happen if we do not use the synchronizedMap() method (and also do not externally synchronize). Then Thread1 and Thread2 may concurrently execute the above code. Thread1 may call keySet() even while Thread2 is concurrently modifying the Map maybe in foo(i.next()). Clearly the results will be unpredicatable.

[This message has been edited by Rahul Rathore (edited March 06, 2001).]
Peter den Haan
author
Ranch Hand

Joined: Apr 20, 2000
Posts: 3252
Originally posted by Mark Savory:
What is the purpose of calling Collections.synchronizedMap()?

Rahul already summarized it perfectly fine -- it makes your Map synchronized. If you don't need a synchronized map, because there's just a single thread accessing it or because you're synchronizing elsewhere, you just use new HashMap().
- Peter
Anand Ramaswamy
Greenhorn

Joined: Mar 05, 2001
Posts: 10
Good i got my fundas cleared
Vishal Mantri
Greenhorn

Joined: Feb 19, 2001
Posts: 2
I am a new member.Today I first time saw such good discussions on java.I wish to appear for certification.I m studying java now.I got much of my fundamentals cleared.Thanks
 
I agree. Here's the link: http://aspose.com/file-tools
 
subject: Synchronized method/blocks.....???????