package com.xuti.increase.utils; import java.lang.ref.Reference; import java.lang.ref.ReferenceQueue; import java.lang.ref.SoftReference; import java.util.HashMap; import java.util.Map; /** * 软引用的集合 * * @author l * */ public class SoftReferenceMap<K, V> extends HashMap<K, V> { // 核心工作:将强引用对象降低成软引用对象 private HashMap<K, MySoftValue<V>> temp; // 账本:装袋子的引用队列 private ReferenceQueue<V> queue; public SoftReferenceMap() { // Object o=new Object();// 占用内存多 // MySoftValue sr=new MySoftValue(o);// o的引用级别降低到软引用对象 // 工作内容 // ①MySoftValueMap的基本功能实现(put、get……) // ②清理空袋子 temp = new HashMap<K, MySoftValue<V>>(); queue=new ReferenceQueue<V>(); } @Override public V get(Object key) { clearNullMySoftValue(); MySoftValue<V> sr = temp.get(key);// 获取袋子 if (sr != null) { // 垃圾回收器清除,则此方法将返回 null return sr.get(); } return null; } @Override public V put(K key, V value) { MySoftValue<V> sr = new MySoftValue<V>(key,value,queue); temp.put(key, sr); return null; } @Override public boolean containsKey(Object key) { clearNullMySoftValue(); // temp.containsKey(key):是否含有袋子 MySoftValue<V> sr = temp.get(key); if(sr!=null) { // return sr.get()!=null; if(sr.get()!=null) { return true; } } return false; } /** * 清理空袋子 */ private void clearNullMySoftValue() { // 目标:发现谁是空袋子 // 方式一:循环temp集合,发现value没有手机,清理 /** * for(Map.Entry item:temp.entrySet()) * { * item.getValue().get(); * } */ // 在内存内存充足的时候,有一定的几率会有误删除,循环==无用功 // 方式二:除了temp集合清楚谁是空袋子外,还有谁清楚? // 谁回收的谁清楚 // 交给一个GC一个"账本",GC在回收对象的时候,记录一下把那个袋子的手机给回收了 // 查账 // 如果存在"一个"立即可用的对象,则从该队列中"移除"此对象并返回。否则此方法立即返回"null"。 MySoftValue<V> sr = (MySoftValue<V>) queue.poll(); while(sr!=null) { // 删除空袋子 temp.remove(sr.key); sr = (MySoftValue<V>) queue.poll(); } } /** * 加强版的袋子,多了key * @author l * */ private class MySoftValue<T> extends SoftReference<T>{ Object key; public MySoftValue(Object key,T referent, ReferenceQueue<? super T> q) { super(referent, q); this.key = key; } } }
软引用的集合
最新推荐文章于 2024-02-16 09:00:00 发布