0%

显式锁

文章字数:372,阅读全文大约需要1分钟

Lock接口是语言层面的锁

一、 常用方法

  • lock()加锁
  • lockInterruptibly()可中断获取锁的过程
  • unlock()释放锁
  • tryLock()尝试获取锁
  • tryLock(long, TimeUnit)可设置获取锁超时

二、对比synchronized

  • 不可中断
  • 不可超时
  • synchronized更简洁
  • 需要锁中断、超时、尝试的时候使用Lock锁,其他尽量使用synchronized

三、可重入锁

  • synchronized是隐式可重入锁
  • ReentrantLockLock的可重入锁实现类,相当于synchronized的代码层实现

四、公平和非公平锁

  • 公平锁,先获取先执行。
  • 非公平锁,新来的执行。效率高,取消了新来的锁的状态切换过程,直接执行。
  • ReentrantLock(true)公平锁
  • ReentrantLock()默认是非公平锁

五、读写锁

  • 排它锁,synchronizedReentrantLock都是排它锁,只允许一个线程获取数据。
  • 读写锁,维护读和写两个锁。适用于读多写少的操作。
  • ReadWriteLock接口下的ReentrantReadWriteLock
  • getlock = readWriteLock.readLock()获取读锁,getlock.lock()
  • setlock = readWriteLock.writeLock()获取写锁,getlock.lock()
    锁的一般用法
    1
    2
    3
    4
    5
    6
    lock.lock();
    try{
    //...
    } finally {
    lock.unlock();
    }

六、Condition接口

  • 实现线程唤醒(通知)功能
  • 每个锁的实现都有getCondition方法可以获取,一个锁可以多个

6.1使用

1
2
3
4
5
6
7
lock.lock();
try{
//...
cond.signal();// 唤醒,因为和等待线程是一一对于的,所以不用All
} finally {
lock.unlock();
}
1
2
3
4
5
6
7
8
9
10
lock.lock();
try{
try{
cond.await();//等待唤醒
}catch(InterruptedException e) {
e.printStackTrace();
}
} finally {
lock.unlock();
}