Synchronizing Threads


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



You perform synchronization when you want to protect sections of code from being accessed by more than one thread at a time. The synchronized keyword, which we show in this phrase, allows us to synchronize a method or code block so that only one thread at a time can execute this method or code block. In this phrase, if one thread is currently executing myMethod(), any other threads attempting to execute the same method, myMethod(), on the same object instance will be locked out of the method until the current thread completes execution and returns from myMethod().

For non-static methods, the synchronization applies only to the object instance that another thread is executing the method on. Other threads may execute the same method, if it is called on a different instance. On the instance that is locked, the lock applies to all synchronized methods of that instance. No thread may call any synchronized methods on an instance for which one thread is already executing a synchronized method. For static methods, only one thread may execute the method at a time.

The synchronized keyword can also be applied to blocks of code. It does not have to cover a complete method. For example, the following block of code is synchronized using this technique:

synchronized(myObject) {    // do something with myObject }


When synchronizing a block of code, you also specify an object to synchronize on. It often makes sense to synchronize on the object containing the block of code, so you would pass the this object as the object being synchronized on, as shown here:

synchronized(this) {    // do something }


The object passed to the synchronized keyword is the object that is locked while a thread is executing the enclosed block of code.

Common places where you would want to use synchronization are where concurrent access by multiple threads might put shared data in an inconsistent state. You have probably heard the term thread-safe. A thread-safe class ensures that no thread uses an object that is in an inconsistent state. In the next block of code, we show an example of a class that could be problematic if we did not make this class thread-safe by using the synchronized keyword on the adjust() method. A class that has instance data members is often a sign of a class that can be problematic in a multithreaded environment. In this example, assume that two threads are running the adjust() method, and it is not synchronized. Thread A executes the line size=size+1 and is interrupted after reading the size value, but before completing the reassignment to size. Thread B now executes and calls the reset() method. This method sets the size variable to 0. Thread B is then interrupted returning control to thread A, thread A now continues executing the size=size+1 statement, setting the value of size to be the value it was prior to being reset, with the addition of 1. The end result is that the reset() method will never appear to have been called. Its effects have been negated by the ill side effects of multithreading. By applying the synchronized keyword to these methods, we prevent this scenario by allowing only one thread to execute either of these methods at a time. The other thread will wait until the current thread has completed the method.

public class ThreadSafeClass {    private int size;    public synchronized void adjust() {      size = size + 1;       if (size >= 100) {          size = 0;      }    }    public synchronized void reset() {       size = 0;    } }


Thread-safe programming only applies to an application that has multiple threads. If you are writing an application that does not use multithreading, you have nothing to worry about and do not need to concern yourself with the concept of thread-safe. Before making that decision though, keep in mind reuse of the application or component that you are writing as well. You might only use a single thread, but is it likely that another project will use your component in a multithreaded environment?

Synchronization can be used to make an object thread-safe, but bear in mind the performance trade-off of using synchronized methods. Calling a synchronized method is substantially slower than calling a non-synchronized method because of the overhead of object locking. So, make sure you only synchronize methods that are truly required to be thread-safe.




JavaT Phrasebook. Essential Code and Commands
Java Phrasebook
ISBN: 0672329077
EAN: 2147483647
Year: 2004
Pages: 166

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net