StampedLock实现读写锁功能的锁对象

  1. 它主要解决的是读写线程比例相差太大,例如共有100个线程
  • 对这个锁进行加锁,比例为99个读线程,1个线程;那么
  • 就会出现写线程总是抢不到锁的情况,这种情况称为:线程“饥饿”
  • 为了避免这种情况,提高效率,那么就出现了这个StampedLock
  1. 注意:
    2.1、StampedLock不是一个重入锁
    2.2、StampedLock不支持Condition
    所有获取锁的方法,都返回一个邮戳(Stamp),Stamp为0表示获取失败,其余都表示成功;
    所有释放锁的方法,都需要一个邮戳(Stamp),这个Stamp必须是和成功获取锁时得到的Stamp一致;
    StampedLock是不可重入的;(如果一个线程已经持有了写锁,再去获取写锁的话就会造成死锁)
    代码
public class StampedLockTest02 {
	
	private static List<Integer> shareDataList = Arrays.asList(1,2,3,4);
	
	private static StampedLock  lock = new StampedLock();
	
	/**
	 * 读方法
	 */
	private static void read(){
		
		//尝试获取读锁
		long stamp  = lock.tryOptimisticRead();
		//如果stamp没有被修改
		if(lock.validate(stamp)){
			try {
			//执行加锁
			stamp = lock.readLock();
			//假设读取操作需要耗时1秒钟
			Thread.sleep(1_000);
			System.out.println(Thread.currentThread().getName()
					+"读到的数据是:"+shareDataList);
			} catch (Exception e) {
				e.printStackTrace();
			}finally{
				lock.unlockRead(stamp);
			}
		}
		
	}
	
	/**
	 * 写方法
	 */
	private static void write(){
		long stamp  = -1;
		stamp = lock.writeLock();
		try {
			//假设写操作需要耗时1秒钟
			Thread.sleep(1_000);
			String threadName = Thread.currentThread().getName();
			System.out.println(threadName+"抢到了锁,开始进行写操作……");
			//将List中的每一个元素进行+1操作
			shareDataList = shareDataList.stream()
					.map(intNum -> ++intNum)
					.collect(Collectors.toList());
			System.out.println(threadName+"写操作完毕!");
			
		} catch (Exception e) {
			e.printStackTrace();
		}finally{
			lock.unlockWrite(stamp);
		}
	}
	
	public static void main(String[] args) {
		
		//创建9个读线程和1个写线程一直去操作shareDataList的数据
		IntStream.rangeClosed(1, 100).forEach(i ->{
			
			if(i==100){
				new Thread("写线程:"){
					@Override
				    public void run() {
						for(;;){
							write();
						}
				    }
				}.start();
				return;
			}
			
			new Thread("读线程"+i+":"){
				@Override
			    public void run() {
					while(true){
						read();
					}
			    }
			}.start();
			
		});
				
		

	}

}

显示结果
在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值