重入鎖,非公平,公平,讀寫鎖
阿新 • • 發佈:2019-03-24
... run 同時 for count join() port 讀鎖 and
重入鎖
package com.thread.demo.safe.lock; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; /** * 重入鎖 * * @author Administrator * */ public class LockDemo1 { private static int count; private static Lock lock = new ReentrantLock();public static void main(String[] args) throws Exception { Thread t1 = new Thread(new MyRunnable(), "AAA"); Thread t2 = new Thread(new MyRunnable(), "BBB"); t2.start(); Thread.sleep(2000); t1.start(); t1.join(); t2.join(); System.out.println("最終結果為:" + count); } static class MyRunnable implements Runnable { public void increase() { // 加鎖 lock.lock(); try { count++; System.out.println(Thread.currentThread().getName() + "計算中...."); Thread.sleep(4000);// 模擬操作耗時 System.out.println(Thread.currentThread().getName() + "計算完成..."); // throw new RuntimeException(); } catch (NumberFormatException e) { e.printStackTrace(); } catch (Exception e) { e.printStackTrace(); } finally { // 解鎖 lock.unlock(); } } public void increase1() { if (lock.tryLock()) { try { count++; //System.out.println(Thread.currentThread().getName() + "計算中...."); Thread.sleep(1000);// 模擬操作耗時 System.out.println(Thread.currentThread().getName() + "計算完成..."); } catch (NumberFormatException e) { e.printStackTrace(); } catch (Exception e) { e.printStackTrace(); } finally { // 解鎖 lock.unlock(); } } else { System.out.println(Thread.currentThread().getName()); try { Thread.sleep(3000); } catch (InterruptedException e) { e.printStackTrace(); } } } public void run() { for (int i = 0; i < 10; i++) { increase1(); } } } }
讀寫鎖
package com.thread.demo.safe.lock; import java.util.Random; import java.util.concurrent.locks.ReadWriteLock; import java.util.concurrent.locks.ReentrantReadWriteLock; class ReadWrite { /* 共享數據,只能一個線程寫數據,可以多個線程讀數據 */ private Object data = null; /* 創建一個讀寫鎖 */ ReadWriteLock rwlock = new ReentrantReadWriteLock(); /** * 讀數據,可以多個線程同時讀, 所以上讀鎖即可 */ public void get() { /* 上讀鎖 */ rwlock.readLock().lock(); try { System.out.println(Thread.currentThread().getName() + " 準備讀數據!"); /* 休眠 */ Thread.sleep((long) (Math.random() * 1000)); System.out.println(Thread.currentThread().getName() + "讀出的數據為 :" + data); } catch (InterruptedException e) { e.printStackTrace(); } finally { rwlock.readLock().unlock(); } } /** * 寫數據,多個線程不能同時 寫 所以必須上寫鎖 * * @param data */ public void put(Object data) { /* 上寫鎖 */ rwlock.writeLock().lock(); try { System.out.println(Thread.currentThread().getName() + " 準備寫數據!"); /* 休眠 */ Thread.sleep((long) (Math.random() * 1000)); this.data = data; System.out.println(Thread.currentThread().getName() + " 寫入的數據: " + data); } catch (Exception e) { e.printStackTrace(); } finally { rwlock.writeLock().unlock(); } } } /** * 測試類 * */ public class ReadWriteLockDemo { public static void main(String[] args) { /* 創建ReadWrite對象 */ final ReadWrite readWrite = new ReadWrite(); /* 創建並啟動3個讀線程 */ for (int i = 0; i < 3; i++) { new Thread(new Runnable() { @Override public void run() { readWrite.get(); } },"AAA"+i).start(); /*創建3個寫線程*/ new Thread(new Runnable() { @Override public void run() { /*隨機寫入一個數*/ readWrite.put(new Random().nextInt(8)); } },"BBB"+i).start(); } } }
讀寫鎖的實例(緩存)
package com.thread.demo.safe.lock; import java.util.Collections; import java.util.HashMap; import java.util.Map; import java.util.concurrent.locks.ReadWriteLock; import java.util.concurrent.locks.ReentrantReadWriteLock; /** * 讀寫鎖的實例 * * @author Administrator * */ public class CacheDemo { // 創建一個緩存對象 static Map<String, Object> cache = Collections.synchronizedMap(new HashMap<>()); static ReadWriteLock rwLock = new ReentrantReadWriteLock(); /** * 定義一個獲取數據的方法 */ public Object getData(String key) { // 開啟讀鎖 rwLock.readLock().lock(); Object value = null; try { // 獲取到緩沖對象中數據 value = cache.get(key); if (value == null) { // 關閉讀鎖 rwLock.readLock().unlock(); // 開啟寫鎖 rwLock.writeLock().lock(); try { value = cache.get(key); // 再次判斷是為空 if (value == null) { // 把數據存儲到緩存中 System.out.println("從db獲取數據"+key); cache.put(key, "key的值"); } } finally { // 釋放寫鎖 rwLock.writeLock().unlock(); } // 打開讀鎖 rwLock.readLock().lock(); } System.out.println("從緩存獲取"); value = cache.get(key); } finally { // 關閉讀鎖 rwLock.readLock().unlock(); } return value; } static class CacheRunnable implements Runnable { @Override public void run() { for (int i = 0; i < 3; i++) { System.out.println(Thread.currentThread().getName()); System.out.println(new CacheDemo().getData(i+"")); } } } public static void main(String[] args) { // 放入數據 //cache.put("1", "1111"); //cache.put("2", 22222); for ( int i = 0; i < 3; i++) { new Thread(new CacheRunnable(),"AAA"+i).start(); } } }
重入鎖,非公平,公平,讀寫鎖