ss the resource protected by this lock } finally { l.unlock(); }} When locking and unlocking occur in different scopes, care must be taken to ensure that all code that is executed while the lock is held is protected by try-finally or try-catch to ensure that the lock is released when necessary.
{@code Lock} implementations provide additional functionalityover the use of {@code synchronized} methods and statements byproviding a non-blocking attempt to acquire a lock ( {@link #tryLock()}), an attempt to acquire the lock that can be interrupted ( {@link #lockInterruptibly}, and an attempt to acquire the lock that can timeout ( {@link #tryLock(long,TimeUnit)}).
A {@code Lock} class can also provide behavior and semanticsthat is quite different from that of the implicit monitor lock, such as guaranteed ordering, non-reentrant usage, or deadlock detection. If an implementation provides such specialized semantics then the implementation must document those semantics.
Note that {@code Lock} instances are just normal objects and canthemselves be used as the target in a {@code synchronized} statement.Acquiring the monitor lock of a {@code Lock} instance has no specified relationshipwith invoking any of the {@link #lock} methods of that instance.It is recommended that to avoid confusion you never use {@code Lock}instances in this way, except within their own implementation.
Except where noted, passing a {@code null} value for anyparameter will result in a {@link NullPointerException} beingthrown.
Memory Synchronization
All {@code Lock} implementations must enforce the samememory synchronization semantics as provided by the built-in monitor lock, as described in The Java Language Specification (17.4 Memory Model):
- A successful {@code lock} operation has the same memorysynchronization effects as a successful Lock action.
- A successful {@code unlock} operation has the samememory synchronization effects as a successful Unlock action.
Unsuccessful locking and unlocking operations, and reentrant locking/unlocking operations, do not require any memory synchronization effects.
Implementation Considerations
The three forms of lock acquisition (interruptible, non-interruptible, and timed) may differ in their performance characteristics, ordering guarantees, or other implementation qualities. Further, the ability to interrupt the ongoing acquisition of a lock may not be available in a given {@code Lock}class. Consequently, an implementation is not required to define exactly the same guarantees or semantics for all three forms of lock acquisition, nor is it required to support interruption of an ongoing lock acquisition. An implementation is required to clearly document the semantics and guarantees provided by each of the locking methods. It must also obey the interruption semantics as defined in this interface, to the extent that interruption of lock acquisition is supported: which is either totally, or only on method entry.
As interruption generally implies cancellation, and checks for interruption are often infrequent, an implementation can favor responding to an interrupt over normal method return. This is true even if it can be shown that the interrupt occurred after another action may have unblocked the thread. An implementation should document this behavior.
@see ReentrantLock
@see Condition
@see ReadWriteLock
@since 1.5
@author Doug Lea