多线程笔记—ReentrantReadWriteLock

ReentrantReadWriteLock

        ReentrantReadWriteLock:读写锁,一个是读操作相关的锁,称为共享锁;另一个是写操作相关的锁,也叫排他锁。也就是多个读锁之间不互斥,读锁与写锁互斥,写锁与写锁互斥。由于ReentrantLock具有完全互斥排他的效果,也就是同一时间只有一个线程在执行ReentrantLock.lock()方法后面的任务。虽然保证了实例变量的安全性,但是效率非常低下,所以JDK中提供了这种读写锁,使用它可以加快运行效率。举例如下:
1.读读共享
//读读共享
public class Service {
private ReentrantReadWriteLock lock=
           new ReentrantReadWriteLock();
public void read(){
	  try{
		  try {
			lock.readLock().lock();
			System.out.println(" 获得读锁 "+Thread
					.currentThread().getName()+" "
					+System.currentTimeMillis());
			Thread.sleep(10000);
		} finally{
			lock.readLock().unlock();
		}
	  }catch(InterruptedException e){
		  e.printStackTrace();
	  }
}
   public static void main(String[] args) {
	   Service service = new Service();
	   ThreadA threadA = new ThreadA(service);
	   threadA.setName("A");
	   ThreadB threadB = new ThreadB(service);
	   threadB.setName("B");
	   threadA.start();
	   threadB.start();	
}
}
public class ThreadA extends Thread{
	private Service service;
	public ThreadA(Service service) {
		super();
		this.service = service;
	}
	@Override
	public void run() {
	    service.read();
	}
}
public class ThreadB extends Thread{
	private Service service;
	public ThreadB(Service service) {
		super();
		this.service = service;
	}
	@Override
	public void run() {
	    service.read();
	}
}
运行结果:
 获得读锁 A 1525617940582
 获得读锁 B 1525617940582
分析:从时间来看,两个线程几乎同时进入lock()方法后面的代码。说明在此使用lock.readLock()读锁可以提高程序运行的效率,允许多个线程同时执行lock();
2.读写互斥
//读写互斥
public class Service {
	private ReentrantReadWriteLock lock=
	           new ReentrantReadWriteLock();
	public void read(){
		try {
			try {
				lock.readLock().lock();
				System.out.println(" 获得读锁 "+Thread
						.currentThread().getName()+" "
						+System.currentTimeMillis());
				Thread.sleep(10000);
			} finally{
				lock.readLock().unlock();
			}
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
	}	
	public void write(){
		try {
			try {
				lock.writeLock().lock();
				System.out.println(" 获得写锁 "+Thread
						.currentThread().getName()+" "
						+System.currentTimeMillis());
				Thread.sleep(10000);
			} finally{
				lock.writeLock().unlock();
			}
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
	}	
	public static void main(String[] args) throws InterruptedException {
		//读写互斥
		Service service = new Service();
		ThreadA a = new ThreadA(service);
		a.setName("A");
		a.start();
		Thread.sleep(1000);
		ThreadB b = new ThreadB(service);
		b.setName("B");
		b.start();
}
}
注:ThreadB中:
@Override
	public void run() {
	    service.write();
	}
运行结果:
获得读锁 A 1525618079549
获得写锁 B 1525618089551
分析:说明“读写”操作是互斥的。
3.写写互斥
 
public class Service {
	private ReentrantReadWriteLock lock=
	           new ReentrantReadWriteLock();
	public void write(){
		try {
			try {
				lock.writeLock().lock();
				System.out.println(" 获得写锁 "+Thread
						.currentThread().getName()+" "
						+System.currentTimeMillis());
				Thread.sleep(10000);
			} finally{
				lock.writeLock().unlock();
			}
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
	}	
	public static void main(String[] args) throws InterruptedException {
//		写写互斥
		Service service = new Service();
		ThreadB b = new ThreadB(service);
		b.setName("B");
		b.start();
		ThreadB b2 = new ThreadB(service);
		b2.setName("B2");
		b2.start();
	}
}
运行结果:
 获得写锁 B 1525618508073
 获得写锁 B2 1525618518076
分析:说明同一时间只允许一个线程执行lock()方法后面的代码。
4.写读互斥
public class Service {
	private ReentrantReadWriteLock lock=
	           new ReentrantReadWriteLock();
	public void write(){
		try {
			try {
				lock.writeLock().lock();
				System.out.println(" 获得写锁 "+Thread
						.currentThread().getName()+" "
						+System.currentTimeMillis());
				Thread.sleep(10000);
			} finally{
				lock.writeLock().unlock();
			}
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
	}	
	
	public void read(){
		try {
			try {
				lock.readLock().lock();
				System.out.println(" 获得读锁 "+Thread
						.currentThread().getName()+" "
						+System.currentTimeMillis());
				Thread.sleep(10000);
			} finally{
				lock.readLock().unlock();
			}
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
	}	
	public static void main(String[] args) throws InterruptedException {
//		写读互斥
		Service service = new Service();
		ThreadB b = new ThreadB(service);
		b.setName("B");
		b.start();
		ThreadA a = new ThreadA(service);
		a.setName("A");
		a.start();
	}
}
运行结果:
获得写锁 B 1525618801176
 获得读锁 A 1525618811178
分析:说明“写读”操作也是互斥的。
5原理分析











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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值