ReentrantLock 锁常用于保证程序的人为顺序执行。
写一个类模拟ReentrantLock类的功能
class MyLock{ private boolean lock = false; private int holdCount = 0; private Thread myThread = null; //当前占用锁的线程 public synchronized void lock(){ //线程同步,只允许一个线程来获取这把锁 Thread currThread = Thread.currentThread(); //当前访问线程 if(lock == true && currThread != myThread){ try { wait(); } catch (InterruptedException e) { e.printStackTrace(); } } //给予锁 myThread = currThread; lock = true; holdCount ++; } public synchronized void unlock(){ Thread currThread = Thread.currentThread(); //当前访问线程 if(currThread == myThread && holdCount>0){ holdCount -- ; if(holdCount == 0){ notifyAll(); lock = false; myThread = null; } } } public int getHoldCount() { return holdCount; } }
当一个线程不能得到一把锁时就会产生等待,等到其他线程释放锁后其将被唤醒,然后拿到所继续运行。
public class Test { public static void main(String[] args) { MyLock myLock = new MyLock(); new Thread(new Runnable() { @Override public void run() { myLock.lock(); System.out.println(Thread.currentThread().getName()+"得到锁:"+myLock.getHoldCount()); myLock.lock(); //可重入锁 System.out.println(Thread.currentThread().getName()+"重入成功:"+myLock.getHoldCount()); myLock.unlock(); System.out.println(Thread.currentThread().getName()+"释放锁:"+myLock.getHoldCount()); myLock.unlock(); System.out.println(Thread.currentThread().getName()+"释放锁:"+myLock.getHoldCount()); } }).start(); new Thread(new Runnable() { @Override public void run() { myLock.lock(); System.out.println(Thread.currentThread().getName()+"得到锁:"+myLock.getHoldCount()); myLock.unlock(); System.out.println(Thread.currentThread().getName()+"释放锁:"+myLock.getHoldCount()); } }).start(); } }
ReentrantLock的使用
public class LockTest { ReentrantLock lock = new ReentrantLock(); public void a() throws InterruptedException { lock.lock(); System.out.println(lock.getHoldCount()); dosomething(); lock.unlock(); System.out.println(lock.getHoldCount()); } public void dosomething() throws InterruptedException { lock.lock(); System.out.println(lock.getHoldCount()); lock.unlock(); System.out.println(lock.getHoldCount()); } public static void main(String[] args) throws InterruptedException { LockTest lockTest = new LockTest(); lockTest.a(); } }