
Java concurrency lib implementations provide additional functionality over the use of synchronized, they providing a non-blocking attempt to acquire a lock (tryLock()), an attempt to acquire the lock that can be interrupted (lockInterruptibly(), and an attempt to acquire the lock that can timeout (tryLock(long, TimeUnit)).
A Lock class is quite different from that of the implicit monitor lock, it can provide guaranteed ordering, reentrant usage and deadlock detection.
An example of some ReentrantLocks using tryLock() :
import java.util.concurrent.TimeUnit; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; public class ReentrantLockingDemo { final Lock lock = new ReentrantLock(); public static void main(final String... args) { new ReentrantLockingDemo().go(); } private void go() { new Thread(newRunable(), "Thread1").start(); new Thread(newRunable(), "Thread2").start(); } private Runnable newRunable() { return new Runnable() { @Override public void run() { do { try { if (lock.tryLock(500, TimeUnit.MILLISECONDS)) { try { System.out.println("locked thread " + Thread.currentThread().getName()); Thread.sleep(1000); } finally { lock.unlock(); System.out.println("unlocked locked thread " + Thread.currentThread().getName()); } break; } else { System.out.println("unable to lock thread " + Thread.currentThread().getName() + " will re try again"); } } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } while (true); } }; } }
the result of running this code is as follows
locked thread Thread2
unable to lock thread Thread1 will re try again
unlocked locked thread Thread2
locked thread Thread1
unlocked locked thread Thread1