手写系列之LRU缓存淘汰算法

LinkedHashMap实现缓存淘汰框架

 

LRU(最近少使用)缓存淘汰算法

LFU(最不经常使用算法)缓存淘汰算法

ARC(自适应缓存替换算法)缓存淘汰算法

FIFO(先进先出算法)缓存淘汰算法

MRU(最近最常使用算法)缓存淘汰算法

 

 

LinkedHashMap基于双向链表实现,可以分为插入或者访问顺序两种,采用双链表的形式保证有序

 

可以根据插入或者读取顺序

 

 

 

LinkedHashMap是HashMap的子类,但是内部还有一个双向链表维护键值对的顺序,每个键值对既位于哈希表中,也位于双向链表中。LinkedHashMap支持两种顺序插入顺序 、 访问顺序

 

 

 

插入顺序:先添加的在前面,后添加的在后面。修改操作不影响顺序

 

执行get/put操作后,其对应的键值对会移动到链表末尾,所以最末尾的是最近访问的,最开始的是最久没有被访问的,这就是访问顺序。
 
手写LRU缓存淘汰:
/**
 * 手写LRU缓存淘汰算法
 * @param <K>
 * @param <V>
 */
public class LruCache<K, V> extends LinkedHashMap<K, V> {
    /**
     * 容量
     */
    private int capacity;

    public LruCache(int capacity) {
        super(capacity, 0.75f, true);
        this.capacity = capacity;
    }

    /**
     * 如果超过存储容量则清除第一个
     *
     * @param eldest
     * @return
     */
    @Override
    protected boolean removeEldestEntry(Map.Entry<K, V> eldest) {
        return size() > capacity;
    }

    public static void main(String[] args) {

        LruCache<String, String> lruCache = new LruCache<>(3);

        //情况1 打印bcd
        lruCache.put("a", "a");
        lruCache.put("b", "b");
        lruCache.put("c", "c");
        lruCache.put("d", "d");
        lruCache.forEach((k, v) -> {
            System.out.println(k + "," + v);
        });
        lruCache.clear();

        //情况2 打印cae
        lruCache.put("a", "a");
        lruCache.put("b", "b");
        lruCache.put("c", "c");
        lruCache.get("a");
        lruCache.put("e", "e");
        lruCache.forEach((k, v) -> {
            System.out.println(k + "," + v);
        });
    }
}

 

 
 
 

 

posted @ 2023-02-03 15:25  山河永慕~  阅读(14)  评论(0编辑  收藏  举报