李林超博客
首页
归档
留言
友链
动态
关于
归档
留言
友链
动态
关于
首页
Java
正文
Java锁--读写锁简介
Leefs
2020-02-23 AM
1503℃
0条
# Java锁--读写锁简介 **1.ReadWriteLock同Lock一样也是一个接口,提供了readLock和writeLock两种锁的操作机制,一个是只读的锁,一个是写锁。** 读锁可以在没有写锁的时候被多个线程同时持有,写锁是独占的(排他的)。 每次只能有一个写线程,但是可以有多个线程并发地读数据。 所有读写锁的实现必须确保写操作对读操作的内存影响。换句话说,一个获得了读锁的线程必须能看到前一个释放的写锁所更新的内容。 理论上,读写锁比互斥锁允许对于共享数据更大程度的并发。与互斥锁相比,读写锁是否能够提高性能取决于读写数据的频率、读取和写入操作的持续时间、以及读线程和写线程之间的竞争。 **2.使用场景** 假设你的程序中涉及到对一些共享资源的读和写操作,且写操作没有读操作那么频繁。 > 例如,最初填充有数据,然后很少修改的集合,同时频繁搜索(例如某种目录)是使用读写锁的理想候选项。 在没有写操作的时候,两个线程同时读一个资源没有任何问题,所以应该允许多个线程能在同时读取共享资源。但是如果有一个线程想去写这些共享资源,就不应该再有其它线程对该资源进行读或写。这就需要一个读/写锁来解决这个问题。 **3.互斥原则** > - 读-读:能共存, > - 读-写:不能共存, > - 写-写:不能共存。 **4.ReadWriteLock接口源码示例** ```java public interface ReadWriteLock { /** * Returns the lock used for reading. */ Lock readLock(); /** * Returns the lock used for writing. */ Lock writeLock(); } ``` **5.没加读写锁代码示例** ```java class MyCache{ private volatile Map
map = new HashMap<>(); public void put(String key,Object value){ System.out.println(Thread.currentThread().getName()+"\t 正在写入:"+key); try { TimeUnit.MILLISECONDS.sleep(300); }catch (InterruptedException e){ e.printStackTrace(); } map.put(key,value); System.out.println(Thread.currentThread().getName()+"\t 写入完成!"); } public void get(String key){ System.out.println(Thread.currentThread().getName()+"\t 正在读取!"); try { TimeUnit.MILLISECONDS.sleep(300); }catch (InterruptedException e){ e.printStackTrace(); } Object result = map.get(key); System.out.println(Thread.currentThread().getName()+"\t 读取完成:"+result); } } public class ReadWriteLockDemo { public static void main(String[] args) { MyCache myCache = new MyCache(); for(int i=1;i<=5;i++){ final int tempInt = i; new Thread(()->{ myCache.put(tempInt+" ",tempInt+" "); },String.valueOf(i)).start(); } for(int i=1;i<=5;i++){ final int tempInt = i; new Thread(()->{ myCache.get(tempInt+""); },String.valueOf(i)).start(); } } } ``` **运行结果** ```java 2 正在写入:2 1 正在写入:1 3 正在写入:3 4 正在写入:4 2 正在读取! 1 正在读取! 5 正在写入:5 3 正在读取! 4 正在读取! 5 正在读取! 4 读取完成:null 5 读取完成:null 3 读取完成:null 5 写入完成! 1 读取完成:null 2 读取完成:null 3 写入完成! 4 写入完成! 1 写入完成! 2 写入完成! ``` 在写入数据的情况下还可以进行数据的读取操作。 **加入读写锁代码示例** ```java class MyCache{ private volatile Map
map = new HashMap<>(); private ReentrantReadWriteLock rwlock = new ReentrantReadWriteLock(); public void put(String key,Object value){ rwlock.writeLock().lock(); try { System.out.println(Thread.currentThread().getName()+"\t 正在写入:"+key); try { TimeUnit.MILLISECONDS.sleep(300); }catch (InterruptedException e){ e.printStackTrace(); } map.put(key,value); System.out.println(Thread.currentThread().getName()+"\t 写入完成!"); }catch (Exception e){ e.printStackTrace(); }finally { rwlock.writeLock().unlock(); } } public void get(String key){ rwlock.readLock().lock(); try { System.out.println(Thread.currentThread().getName()+"\t 正在读取!"); try { TimeUnit.MILLISECONDS.sleep(300); }catch (InterruptedException e){ e.printStackTrace(); } Object result = map.get(key); System.out.println(Thread.currentThread().getName()+"\t 读取完成:"+result); }catch (Exception e){ e.printStackTrace(); }finally { rwlock.readLock().unlock(); } } } public class ReadWriteLockDemo { public static void main(String[] args) { MyCache myCache = new MyCache(); for(int i=1;i<=5;i++){ final int tempInt = i; new Thread(()->{ myCache.put(tempInt+" ",tempInt+" "); },String.valueOf(i)).start(); } for(int i=1;i<=5;i++){ final int tempInt = i; new Thread(()->{ myCache.get(tempInt+""); },String.valueOf(i)).start(); } } } ``` **运行结果** ```java 1 正在写入:1 1 写入完成! 2 正在写入:2 2 写入完成! 3 正在写入:3 3 写入完成! 4 正在写入:4 4 写入完成! 5 正在写入:5 5 写入完成! 1 正在读取! 2 正在读取! 3 正在读取! 4 正在读取! 5 正在读取! 2 读取完成:null 1 读取完成:null 4 读取完成:null 3 读取完成:null 5 读取完成:null ``` 在线程写入的时候不允许执行其他线程方法,在读取时候可以线程争抢资源。 *附:参考原文链接https://blog.csdn.net/j080624/article/details/82790372*
标签:
并发编程
,
锁
非特殊说明,本博所有文章均为博主原创。
如若转载,请注明出处:
https://lilinchao.com/archives/640.html
上一篇
集合类不安全之并发修改异常
下一篇
Java锁--自旋锁简介
取消回复
评论啦~
提交评论
栏目分类
随笔
2
Java
326
大数据
229
工具
31
其它
25
GO
47
标签云
LeetCode刷题
SpringCloud
Flink
gorm
Scala
Filter
Hbase
Eclipse
Hadoop
nginx
Typora
设计模式
MySQL
Golang
Linux
Spark SQL
MyBatis-Plus
线程池
Flume
Yarn
Git
Livy
Java
Spring
Elasticsearch
HDFS
JavaSE
数据结构和算法
SpringBoot
数学
友情链接
申请
范明明
庄严博客
Mx
陶小桃Blog
虫洞