题目

146. LRU缓存机制

思路

  • 利用双链表和HashMap来解题
  • 看到链表题目,我们可以使用头尾结点可以更好进行链表操作和边界判断等
  • 还需要使用size变量来存储双链表的当前长度
  • 调用get,如果存在的话,我们可以调用将在双链表中的结点通过修改指针移动到第一个;如果调用put,我们先判断是否存在该结点,如果不存在,可直接将链接插入即可,同时size++,如果存在的话,先删除原来的结点,再将新结点push到头部即可

代码

class LRUCache {
class Node {
int key;
int val;
Node pre;
Node next; public Node() {} public Node(int key, int val) {
this.key = key;
this.val = val;
}
} // 哈希表中的node和双链表的node是同一个结点
private HashMap<Integer, Node> cache;
private Node dummyHead;
private Node dummyTail;
private int size;
private int capacity; public LRUCache(int capacity) {
cache = new HashMap<>();
dummyHead = new Node();
dummyTail = new Node();
dummyHead.next = dummyTail;
dummyTail.pre = dummyHead;
this.capacity = capacity;
this.size = 0;
} public int get(int key) {
// 先获取看看结点存不存在
Node node = cache.get(key);
// 如果存在的话,将当前访问的结点移动到链表头,并且返回值
if (node != null) {
moveToHead(node);
return node.val;
}
// 不存在的话就返回-1
return -1;
} public void put(int key, int value) {
// 也是先看看结点是否存在
Node node = cache.get(key);
// 如果存在,那么要做的操作就是将结点移动到链表头,然后更新结点值即可
if (node != null) {
node.val = value;
moveToHead(node);
} else {
// 如果不存在的话我们就要创建新结点插入
Node newNode = new Node(key, value);
// 先添加到哈希表中
cache.put(key, newNode);
// 再添加到链表中
addToHead(newNode);
// 并且长度+1
size++;
// 因为我们设定最大容量,我们还要判断新put的结点后,容量是否超过了capacity,超过了话,删除最后一个结点,并且长度-1
if (size > capacity) {
Node tail = removeTail();
cache.remove(tail.key);
size--;
}
}
} /**
* 将node移动到最前面
*/
private void moveToHead(Node node) {
if (size > 0 && size <= capacity) {
remove(node);
addToHead(node);
}
} /**
* 删除node结点
*/
private void remove(Node node) {
if (size > 0) {
node.pre.next = node.next;
node.next.pre = node.pre;
}
} /**
* 删除最后一个结点
*/
private Node removeTail() {
if (size > 0) {
Node node = dummyTail.pre;
remove(node);
return node;
}
return null;
} /**
* 添加新结点到第一位去
*/
private void addToHead(Node node) {
node.next = dummyHead.next;
dummyHead.next = node;
node.next.pre = node;
node.pre = dummyHead;
}
}

复杂度分析

  • 时间复杂度:\(O(1)\)
  • 空间复杂度:\(O(N)\),其中 N 为初始化的 capacity 容量

力扣 - 146. LRU缓存机制的更多相关文章

  1. 【golang必备算法】 Letecode 146. LRU 缓存机制

    力扣链接:146. LRU 缓存机制 思路:哈希表 + 双向链表 为什么必须要用双向链表? 因为我们需要删除操作.删除一个节点不光要得到该节点本身的指针,也需要操作其前驱节点的指针,而双向链表才能支持 ...

  2. Java实现 LeetCode 146 LRU缓存机制

    146. LRU缓存机制 运用你所掌握的数据结构,设计和实现一个 LRU (最近最少使用) 缓存机制.它应该支持以下操作: 获取数据 get 和 写入数据 put . 获取数据 get(key) - ...

  3. 146. LRU 缓存机制 + 哈希表 + 自定义双向链表

    146. LRU 缓存机制 LeetCode-146 题目描述 题解分析 java代码 package com.walegarrett.interview; /** * @Author WaleGar ...

  4. 【力扣】146. LRU缓存机制

    运用你所掌握的数据结构,设计和实现一个  LRU (最近最少使用) 缓存机制.它应该支持以下操作: 获取数据 get 和 写入数据 put . 获取数据 get(key) - 如果关键字 (key) ...

  5. [Leetcode]146.LRU缓存机制

    Leetcode难题,题目为: 运用你所掌握的数据结构,设计和实现一个  LRU (最近最少使用) 缓存机制.它应该支持以下操作: 获取数据 get 和 写入数据 put . 获取数据 get(key ...

  6. 146. LRU缓存机制

    题目描述 运用你所掌握的数据结构,设计和实现一个LRU (最近最少使用) 缓存机制.它应该支持以下操作: 获取数据 get 和 写入数据 put . 获取数据 get(key) - 如果密钥 (key ...

  7. leetcode:146. LRU缓存机制

    题目描述: 运用你所掌握的数据结构,设计和实现一个  LRU (最近最少使用) 缓存机制.它应该支持以下操作: 获取数据 get 和 写入数据 put . 获取数据 get(key) - 如果密钥 ( ...

  8. LeetCode 146. LRU缓存机制(LRU Cache)

    题目描述 运用你所掌握的数据结构,设计和实现一个  LRU (最近最少使用) 缓存机制.它应该支持以下操作: 获取数据 get 和 写入数据 put . 获取数据 get(key) - 如果密钥 (k ...

  9. Leetcode 146. LRU 缓存机制

    前言 缓存是一种提高数据读取性能的技术,在计算机中cpu和主内存之间读取数据存在差异,CPU和主内存之间有CPU缓存,而且在内存和硬盘有内存缓存.当主存容量远大于CPU缓存,或磁盘容量远大于主存时,哪 ...

随机推荐

  1. PicGo图床与Typora(PicGo+Typora+GitHub的完整设置)

    PicGo图床与Typora(PicGo+Typora+GitHub的完整设置) 如何更方便的用markdown写文章,接下来按照我的步骤来,你一定可以的,这个文章包含了GitHub图床配置.PicG ...

  2. Python基础笔记2-ruamel.yaml读写yaml文件

    上一篇笔记记录了Python中的pyyaml库对yaml文件进行读写,但了解到ruamel.yaml也能对yaml文件进行读写,于是想尝试一下它的用法. 一,注意 这里首先要更正一下网上大部分博客的说 ...

  3. Js中Currying的应用

    Js中Currying的应用 柯里化Currying是把接受多个参数的函数变换成接受一个单一参数的函数,并且返回接受余下的参数且返回结果的新函数的技术,是函数式编程应用. 描述 如果说函数式编程中有两 ...

  4. day06 Pyhton学习

    一.昨日内容回顾 字典: 由{}表示,内部存储key:value 要求: key不能重复 key必须可哈希.不可变 value没有限制 没有索引和切片 增删改查 新增: dic.[新key]=valu ...

  5. linux(centos8):jmeter5.3并发测试实例(参数在范围内随机取值)

    一,测试的url地址说明: 1,这是一个秒杀功能的url: http://127.0.0.1:8080/second/skusecond?actid=2020&skuid=cpugreen&a ...

  6. nginx安全:配置网站图片防盗链

    一,为什么要做防盗链? 1,什么是盗链? 比如某人有一个A网站, 他不愿自己存储图片,(因为磁盘和带宽都有成本) 就在自己A网站的页面上直接插入B网站的图片, 从而为自己吸引流量,这就是盗链 2,为什 ...

  7. css和xpath定位补充

    定位的网页的地址:https://item.jd.com/100000323510.htmlxpath绝对定位: 1 以"/"开头的是绝对定位 2 /html/body/div[1 ...

  8. 正则匹配img标签 蜘蛛 爬取分析 新闻采集

    string ostr = "aaaaaa<img asddsa src=\"\" asddsasd />aaaaaaa<img src=\" ...

  9. js一些注意事项

    0.正则表达式,千万不能加引号 1.json对象的key必须用双引号,否则parse时可能出错: json对象不能直接存储时间对象,需要将时间对象加双引号转为字符串,存储,然后对表示时间的属性进行ne ...

  10. gethub网址链接

    https://github.com/fraser-in-school/suduku 之前这个网址是手动提交的,现在从新更新下,这是用Visio studio提交的,应该不会缺少并不必要的文件 htt ...