LRU
在很多缓存失效策略中会涉及,本质是一种更公平的节约资源策略
比如使用redis缓存数据,不可能将所有资源都缓存起来,内存耗不起
但也不能一刀切的设定一个过期时间,自动过期,因为可能热点数据它经常被访问到
LRU算法思想应运而生,LRU是Least Recently Used的缩写,即最近最少使用
在资源有限的情况下,我们要将最近最少使用的对象解除资源占用,给更需要的场景
java中的LinkedHashMap就有自带的实现LRU
简单说一下LinkedHashMap这种数据结构,本质是HashMap+双向链表,不仅有HashMap的特性,还能维护元素的顺序,示意图如下
使用LinkedHashMap实现简单的LRU
杨家将父子打扑克,跑得快,一局只能有四个人参与,但杨家将父子有八人
约定赢了(被访问次数多)的前两位留下,输了(访问次数少)的出局,给后面的新进的腾位置
package cn.com.suntree.utils.myself;
import java.util.LinkedHashMap;
import java.util.Map;
import java.util.Set;
/**
* 自定义LRU 类
* @param <K>
* @param <V>
*/
public class LRU<K, V> {
private final float loadFactory = 0.75f; //使用LinkedHashMap容量,负载因子使用默认的0.75
private LinkedHashMap<K, V> map;
public LRU(int maxCacheSize) {
int capacity = (int)Math.ceil(maxCacheSize / this.loadFactory) + 1;// HashMap达到容量就进行扩容,if ((size >= threshold),因此需要+1
map = new LinkedHashMap<K, V>(capacity, loadFactory, true) {
// accessOrder为true表示LRU
@Override
protected boolean removeEldestEntry(Map.Entry eldest) {
// 重写removeEldestEntry,当容量超过maxCacheSize会移除first
return size() > maxCacheSize;
}
};
}
/**
* 都是调用 LinkedHashMap 的方法
*/
public void put(K key, V value) {
map.put(key, value);
}
public V get(K key) {
return map.get(key);
}
public void remove(K key) {
map.remove(key);
}
public boolean contain(K key) {
return map.containsKey(key);
}
/**
* 跑得快,一局四个人,轮流来,最先进场的先出来
* @param args
*/
public static void mai