• Post Reply Bookmark Topic Watch Topic
  • New Topic

java synchronization

 
amithk kumar
Greenhorn
Posts: 12
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator




The main program








i have created a class called counter and initialized a variable c . When called on increment method it increments by 1. When called on decrement method it decreases by 1.

There is one more method called getVal which will return the c value. These methods i have added synchronized keyword for the methods


In the main program i am sharing the counter object in the loop. I am looping and creating threads and starting them but while running even though i have added synchronized method iam getting output like this


the increment case Thread--->72
the value case Thread--->72
Thread--->72 incremented 1
the decrement case Thread--->72
the value case Thread--->72
Thread--->72 decremented 0
the increment case Thread--->76
the value case Thread--->76
Thread--->76 incremented 1
the decrement case Thread--->76
the value case Thread--->76
Thread--->76 decremented 0
the increment case Thread--->80
the value case Thread--->80
Thread--->80 incremented 1
the increment case Thread--->22
the increment case Thread--->124
the increment case Thread--->2
the increment case Thread--->116
the value case Thread--->116
the increment case Thread--->120
the value case Thread--->120
Thread--->120 incremented 6
the decrement case Thread--->120

Thread 72 and Thread 76 are printing correctly first it is increasing the value so it is 1 and then decreasing value so it is 0.

but if you see Thread 22 and Thread 124 and Thread 2 and so on the value of c variable reached to 6 . This is what iam confused even though adding synchronized keyword it is behaving very different


But if i add synchronized block like this in run

iam getting the expected output .Why it is happening , whether the synchronized keyword for those methods are not enough?do i have to use the synchronize for run only?

Can someone explain about re entrancy according to this code?
 
Mike. J. Thompson
Bartender
Posts: 689
17
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
The synchronized keyword locks on the current object (so effectively on this). This means that when one thread enters any of those methods it will acquire the lock before it enters it. No other thread will be able to enter any of those methods while that thread has the lock. But the other threads will still be running, and on modern CPU's that have multiple cores those threads can literally be running at the same time. So when you start multiple threads that all want to run those methods in the same order you are going to end up with a situation where multiple threads try to run one of the methods at the same time.

When that happens, one of them will win and be allowed into the method. The other threads will block at the start of the method, waiting until they can get the lock. When the thread that won finishes the method it will release the lock and go back to the run() method to continue with the next instruction. At that point any of the waiting threads blocked on the method can acquire the lock and go execute the method. It isn't deterministic which thread will get the lock, so you can't have any idea exactly what will happen each time you run the code.

What you have here is called a race condition. You want the code to always increment the variable once and then decrement the variable once, but your synchronization does not guarantee that that will happen. All you have done is ensured that only one thread can be in any of the methods at once, but you haven't ensured that that thread will then run the following methods before another thread gets a go.

You will need to synchronize all three method calls (in the run() method) if you want to ensure that all three methods are called in order by each thread before any other thread can execute.
 
  • Post Reply Bookmark Topic Watch Topic
  • New Topic
Boost this thread!