赞
踩
ReentrantReadWriteLock 是Java中提供的一种读写锁实现,它允许多个线程同时读取共享资源,但在写操作时需要独占访问。它是对传统互斥锁的一种改进,可以提高并发性能。
读写锁的主要目的是在读多写少的场景下,提供更高的并发性能。当多个线程只需读取共享资源时,可以同时获得读锁,从而实现并发读取。而当有线程需要对共享资源进行写操作时,它必须独占地获取写锁,在此期间,其他线程无法获取读锁或写锁,从而确保数据的一致性和完整性。
读写锁的特性如下:
创建一个ReentrantReadWriteLock
对象
ReentrantReadWriteLock rwLock = new ReentrantReadWriteLock();
获取读锁
rwLock.readLock().lock();
try {
// 访问共享资源的读操作
} finally {
rwLock.readLock().unlock();
}
获取写锁
rwLock.writeLock().lock();
try {
// 访问共享资源的写操作
} finally {
rwLock.writeLock().unlock();
}
SharedData 类使用 ReentrantReadWriteLock 实现了读写锁机制。多个线程可以同时获取读锁进行读操作,但只有一个线程可以获取写锁进行写操作,以提高读操作的并发性能。
class SharedData { private Map<String, String> data = new HashMap<>(); private ReentrantReadWriteLock lock = new ReentrantReadWriteLock(); public void put(String key, String value) { lock.writeLock().lock(); try { data.put(key, value); } finally { lock.writeLock().unlock(); } } public String get(String key) { lock.readLock().lock(); try { return data.get(key); } finally { lock.readLock().unlock(); } } }
测试方法:创建1个写线程,10个读线程。模拟读多写少的场景。
private void test(){ SharedData data = new SharedData(); List<Thread> threads = new ArrayList(); for(int i = 1; i<= 1; i++){ Thread t = new Thread(()->{ for(int j=0; j< 100000; j++){ try { String text = Thread.currentThread().getName()+" 写数据 "+ j; data.put("SharedData", text); System.out.println(text); Thread.sleep(3000); } catch (InterruptedException e) { e.printStackTrace(); } } }); t.setName("写线程"+i); threads.add(t); } for(int i = 1; i<= 10; i++){ Thread t = new Thread(()->{ for(int j=0; j< 100000; j++){ try { String result = data.get("SharedData"); System.out.println(Thread.currentThread().getName()+" 读取 "+result); Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } } }); t.setName("读线程"+i); threads.add(t); } for(Thread t : threads){ t.start(); } for(Thread t : threads){ try { t.join(); } catch (InterruptedException e) { e.printStackTrace(); } } }
以下是完整示例代码
package top.yiqifu.study.p004_thread; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.concurrent.locks.ReentrantReadWriteLock; public class Test062_ReentrantReadWriteLock { public static void main(String[] args) { Test062_ReentrantReadWriteLock test = new Test062_ReentrantReadWriteLock(); test.test(); } private void test(){ SharedData data = new SharedData(); List<Thread> threads = new ArrayList(); for(int i = 1; i<= 1; i++){ Thread t = new Thread(()->{ for(int j=0; j< 100000; j++){ try { String text = Thread.currentThread().getName()+" 写数据 "+ j; data.put("SharedData", text); System.out.println(text); Thread.sleep(3000); } catch (InterruptedException e) { e.printStackTrace(); } } }); t.setName("写线程"+i); threads.add(t); } for(int i = 1; i<= 10; i++){ Thread t = new Thread(()->{ for(int j=0; j< 100000; j++){ try { String result = data.get("SharedData"); System.out.println(Thread.currentThread().getName()+" 读取 "+result); Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } } }); t.setName("读线程"+i); threads.add(t); } for(Thread t : threads){ t.start(); } for(Thread t : threads){ try { t.join(); } catch (InterruptedException e) { e.printStackTrace(); } } } class SharedData { private Map<String, String> data = new HashMap<>(); private ReentrantReadWriteLock lock = new ReentrantReadWriteLock(); public void put(String key, String value) { // 写锁 lock.writeLock().lock(); try { data.put(key, value); } finally { lock.writeLock().unlock(); } } public String get(String key) { // 读锁 lock.readLock().lock(); try { return data.get(key); } finally { lock.readLock().unlock(); } } } }
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。