Java Reference
In-Depth Information
finally {
// Release the lock
myLock.unlock();
}
}
}
You may wonder why you would use the code structure listed in Listing 6-30 when you could have used the
synchronized
keyword to achieve the same effect, like so:
public void updateResource() {
// Acquire the lock and the lock will be released automatically by the
// JVM when your code exits the block
synchronized (this) {
// Logic for updating/reading the shared resource goes here
}
}
You are correct in thinking that using the
synchronized
keyword would have been better in this case. It is much
simpler and less error prone to use the
synchronized
keyword in such situations. The power of using the new
Lock
interface becomes evident when you come across situations where using the
synchronized
keyword is not possible
or very cumbersome. For example, if you want to acquire the lock in the
updateResource()
method and release it in
some other methods, you cannot use the
synchronized
keyword. If you need to acquire two locks to work with a shared
resource and if only one lock is available, you want to do something else rather than waiting for the other lock. If you
use the
synchronized
keyword or the
lock()
method of the
Lock
interface to acquire a lock, the call blocks if the lock
is not available immediately, which gives you no option to back off once you asked for the lock. Such blocked threads
cannot be interrupted either. The two methods of the
Lock
interface,
tryLock()
and
lockInterruptibly()
, give you
the ability to try to acquire a lock (rather than acquire a lock or block). The thread that has acquired the lock can be
interrupted if it is blocked. The syntax to acquire and release a lock using the
Lock
interface should use a
try-finally
or a
try-catch-finally
block structure to avoid unintended bugs by placing the
unlock()
call in a
finally
block.
You will solve a classic synchronization problem known as the dining-philosophers problem using the explicit
lock constructs. The problem goes like this: five philosophers spend all of their time either thinking or eating. They
sit around a circular table with five chairs and five forks, as shown in Figure
6-7
. There are only five forks and all five
philosophers need to pick the two nearest (one from his left and one from his right) forks to eat.
Figure 6-7.
Five philosophers at a dining table