并发操作之——ReentrantReadWriteLock

并发操作

并发操作之——ReentrantReadWriteLock.



并发操作之——ReentrantReadWriteLock

高并发环境下多线程加锁的问题。


一、ReentrantReadWriteLock

1、读写锁

读写锁接口readWriteLock接口的一种实现,实现了读写分离。

2、公平和非公平锁

支持公平和非公平锁,底层也是AQS实现。

3、锁降级

允许从写锁降级为读锁
流程: 先获取写锁,然后获取读锁,最后释放写锁;但不能从读锁升级到写锁。

4、重入

读锁后还可以获取读锁,获取写锁之后可以获取写锁和读锁。
在这里插入图片描述

5、核心

读锁是共享的,写锁是独占的。读和读之间不会互斥,读和写、写和读之间才会互斥,主要是提升了读写的性能。
在这里插入图片描述

二、ReentrantReadWriteLock应用场景

应用场景: 读多写少,比如设计一个缓存组件 或 提高Collection的并发性

源码本身提供案例,示例一:用ReenTrantReadWriteLock做读写锁分离操作

class CachedData {
    Object data;
    volatile boolean cacheValid;
    final ReentrantReadWriteLock rwl = new ReentrantReadWriteLock();
 
    void processCachedData() {
      rwl.readLock().lock();
      if (!cacheValid) {
        // Must release read lock before acquiring write lock
        rwl.readLock().unlock();
        rwl.writeLock().lock();
        try {
          // Recheck state because another thread might have
          // acquired write lock and changed state before we did.
          if (!cacheValid) {
            data = ...
            cacheValid = true;
          }
          // Downgrade by acquiring read lock before releasing write lock
          rwl.readLock().lock();
        } finally {
          rwl.writeLock().unlock(); // Unlock write, still hold read
        }
      }
 
      try {
        use(data);
      } finally {
        rwl.readLock().unlock();
      }
    }
  }}

源码本身提供案例,示例二:实现一个线程安全的map

 class RWDictionary {
    private final Map<String, Data> m = new TreeMap<String, Data>();
    private final ReentrantReadWriteLock rwl = new ReentrantReadWriteLock();
    private final Lock r = rwl.readLock();
    private final Lock w = rwl.writeLock();
 
    public Data get(String key) {
      r.lock();
      try { return m.get(key); }
      finally { r.unlock(); }
    }
    public String[] allKeys() {
      r.lock();
      try { return m.keySet().toArray(); }
      finally { r.unlock(); }
    }
    public Data put(String key, Data value) {
      w.lock();
      try { return m.put(key, value); }
      finally { w.unlock(); }
    }
    public void clear() {
      w.lock();
      try { m.clear(); }
      finally { w.unlock(); }
    }
  }}

三、ReentrantReadWriteLock和ReenTrantLock的区别

在这里插入图片描述


总结

最主要的区别是ReenTrantReadWriteLock对比ReenTrantLock可以实现读写锁分离,再就是ReenTrantReadWriteLock特殊的重入锁机制。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

RobertTeacher

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值