Cache的简单实现(3)

流过昼夜 提交于 2019-11-29 02:12:19

今天参考MyBatis框架对LruCache进行了一个简单的实现,LruCache,顾名思义,实现了Lru算法的缓存容器,

而Lru算法,则是当容器已满还要添加数据的时候,移除最近最不常使用的数据,保留最近最常使用的数据

 

以下是我参考MyBatis框架中的LruCache写的一个简单实现

 1 package com.company.cache;
 2 
 3 import java.util.LinkedHashMap;
 4 import java.util.Map;
 5 
 6 public class LruCache implements Cache {
 7     private Cache cache;
 8     private Map<Object, Object> map;
 9     //定义一个变量来接收过时的Key
10     private Object oldKey;
11     public LruCache(Cache cache) {
12         this.cache = cache;
13         setSize(3);
14     }
15     public void setSize(final int maxCap){
16         //使用匿名内部类继承LinkedHashMap来实现Lru算法,同时限定Cache大小
17         map = new LinkedHashMap<Object, Object>(maxCap, 0.75f, true){
18             private static final long serialVersionUID = 2574527887416129186L;
19             
20             /**
21              * 重写LinkedHashMap中的removeEldestEntry方法
22              * 这个方法在LinkedHashMap每次put时都会自动调用
23              * 重写之后,当存放数据时,map的数据量大于指定的容量的话,
24              * 就会把最不常使用的key赋值给我们在LruCache中定义的oldKey,
25              * 同时map删除这个key
26              * @param eldest
27              * @return
28              */
29             @Override
30             protected boolean removeEldestEntry(java.util.Map.Entry<Object, Object> eldest) {
31                 boolean b = size() > maxCap;
32                 if(b){
33                     oldKey = eldest.getKey();
34                 }
35                 return b;
36             }
37         };
38     }
39     @Override
40     public void putObject(Object key, Object value) {
41         cache.putObject(key, value);
42         //调用在类中定义的私有方法
43         checkObject(key);
44     }
45     //当外部调用LruCache的getObject方法时,内部调用map的get方法以控制访问顺序
46     @Override
47     public Object getObject(Object key) {
48         map.get(key);
49         return cache.getObject(key);
50     }
51     //移除元素的同时,map移除对应的key
52     @Override
53     public Object removeObject(Object key) {
54         map.remove(key);
55         return cache.removeObject(key);
56     }
57     @Override
58     public String toString() {
59         return cache.toString();
60     }
61     //检测oldKey是否为null,若是不为null的话则移除oldKey及对应的值,并把oldKey初始化为null
62     private void checkObject(Object key){
63         map.put(key, key);
64         if(oldKey != null){
65             cache.removeObject(oldKey);
66             oldKey = null;
67         }
68     }

内存的Lru算法实际上是基于LinkedHashMap来实现的,以LinkedHashMap来控制访问顺序,用内部封装的cache来存放数据,当put相同元素和get时,将该元素的访问量+1,若是超出容量限制,则将最不常使用的元素移除

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!