LRU 最近最少用算法的实现

本文详细介绍了LRU缓存淘汰机制的工作流程,选择双向链表结合哈希表的数据结构,以及如何在Java中自定义实现LRU。通过实例展示了LRU的插入、替换操作,并对自定义实现进行了测试,验证其正确性。
摘要由CSDN通过智能技术生成

LRU

学过 OS 的都知道,缓存有几个缓存淘汰机制,其中最有名的,就是 LRU 缓存淘汰机制

即在缓存快满的情况下,将最近使用最少的内存空间腾出来

那这个算法具体是怎么实现的呢?下面就让我们来探究一下

一、LRU 工作流程

我们先来看一下,LRU 具体是个什么流程:

假设我们的缓存大小为 3,目前已经存入了三个数 1,2,3

[1,2,3]

这时我们使用了2,那 2 就是最近使用的数,被提到最前面:

[1,3,2]

这时我们想插入一个 4,因为 1 是最近最少用的值,我们将 1 替换掉:

[3,2,4]

然后,我们又要去用 3:

[2,4,3]

至此,我们大致能了解 LRU 具体是要实现一个什么东西了

二、数据结构选型

我们可以发现,数据的初入,与队列十分相似,那么数据存储的数据结构我们就选择队列了,并且队列的实现我们使用 双向链表

但是,双向链表的查找时间复杂度为 O(n) ,为了让时间复杂度降为 O(1),我们可以将其与哈希表混用,实现一个复合数据结构哈希链表

哈希链表

三、具体实现

Java 中,有封装好的数据结构 LinkedHashMap,可以用来实现 LRU ,但是直接使用它我们这篇文章就没有什么意义了,我们还是要自己造一回轮子。

上回说到,实现 LRU,我们要使用复合数据结构 哈希链表,我们这里,就先实现双端队列,再去实现哈希链表

  • 节点数据结构:
public class DNode {
   
    // 节点中存储 key 值,是为了方便在 哈希链表中,删除 hash 表中的 key 值
    public Integer key;
    public Integer val;
    public DNode next;
    public DNode pre;

    public DNode(Integer val) {
   
        this.val = val;
    }

    public DNode(Integer key, Integer val) {
   
        this.key = key;
        this.val = val;
    }
}
  • 双端队列:
public class DoubleList {
   
    private int size=0;

    DNode head = null;
    DNode tail = null;

    public DoubleList() {
   }

    public void addLast(DNode node) {
   
        if (head==null) {
   
            head=node;
            tail=head;
        } else {
   
            tail.next=node;
            tail.next.pre=tail;
            tail=tail.next;
        }
        ++size;
    }

    public DNode removeFirst() {
   
        if (size<=0) return null;
        DNode tmp = head;
        if (head.next==null) {
   
            head=null;
            tail=null;
        } else {
   
            head.next.pre=null;
            head=head.next;
            tmp.next=null;
        }
        -- size
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

FARO_Z

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值