146. LRU 缓存机制

LeetCode-146

题目描述

题解分析

java代码

package com.walegarrett.interview;

/**
* @Author WaleGarrett
* @Date 2021/2/19 8:51
*/ import java.util.HashMap;
import java.util.Map; /**
* 题目描述:运用你所掌握的数据结构,设计和实现一个  LRU (最近最少使用) 缓存机制 。
* 实现 LRUCache 类:
* LRUCache(int capacity) 以正整数作为容量 capacity 初始化 LRU 缓存
* int get(int key) 如果关键字 key 存在于缓存中,则返回关键字的值,否则返回 -1 。
* void put(int key, int value) 如果关键字已经存在,则变更其数据值;如果关键字不存在,则插入该组「关键字-值」。
* 当缓存容量达到上限时,它应该在写入新数据之前删除最久未使用的数据值,从而为新的数据值留出空间。
*  
* 进阶:你是否可以在 O(1) 时间复杂度内完成这两种操作?
*/
public class LeetCode_146 {
private DLinkedNode head,tail;//伪头结点和尾结点
private int size,capacity;
private Map<Integer,DLinkedNode> map = new HashMap<>();
public LeetCode_146(int capacity) {
this.size = 0;
this.capacity = capacity;
//创建伪头结点和伪尾结点
head = new DLinkedNode();
tail = new DLinkedNode();
head.next = tail;
tail.pre = head;
} public int get(int key) {
DLinkedNode node = map.get(key);
if(node == null)
return -1;
//如果key存在,因为这是最新使用的将其移动到头结点
removeToHead(node);
return node.value;
} public void put(int key, int value) {
DLinkedNode node = map.get(key);
if(node == null){
//如果key不存在,则创建一个新的结点
DLinkedNode newNode = new DLinkedNode(key, value);
map.put(key, newNode);
//添加到链表头部
addToHead(newNode);
++size;
//判断个数是否超出容量
if(size>capacity){
//删除尾部结点
DLinkedNode tail = removeTail();
//删除哈希表中对应的项
map.remove(tail.key);
--size;
}
}else{
//如果key存在,首先更新哈希表中的value
node.value = value;
map.put(key, node);
//该结点为最近访问的结点,添加到头结点
removeToHead(node);
}
}
/**
* 双向链表的自定义实现
*/
class DLinkedNode{
int key,value;
DLinkedNode pre,next;
public DLinkedNode(){}
public DLinkedNode(int _key, int _value){key = _key; value=_value;}
} /**
* 将新结点放置到头结点
* @param node
*/
private void addToHead(DLinkedNode node){
node.pre = head;
node.next = head.next;
head.next.pre = node;
head.next = node;
} /**
* 移除当前结点
* @param node
*/
private void removeNode(DLinkedNode node){
node.pre.next = node.next;
node.next.pre = node.pre;
} /**
* 将当前结点移动到头结点
* @param node
*/
private void removeToHead(DLinkedNode node){
removeNode(node);
addToHead(node);
} /**
* 删除尾结点
*/
private DLinkedNode removeTail(){
DLinkedNode realTail = tail.pre;
removeNode(realTail);
return realTail;
}
}

复杂度分析

146. LRU 缓存机制 + 哈希表 + 自定义双向链表的更多相关文章

  1. 力扣 - 146. LRU缓存机制

    目录 题目 思路 代码 复杂度分析 题目 146. LRU缓存机制 思路 利用双链表和HashMap来解题 看到链表题目,我们可以使用头尾结点可以更好进行链表操作和边界判断等 还需要使用size变量来 ...

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

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

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

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

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

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

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

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

  6. Leetcode 146. LRU 缓存机制

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

  7. 146. LRU缓存机制

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

  8. leetcode:146. LRU缓存机制

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

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

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

随机推荐

  1. dsu on tree ——附带buff的暴力解法

    这篇博客只是简单叙述思想(因为ML太弱了),具体例题请转其他博客. dsu on tree,许多OI将其归于启发式合并,当然如果你能理解更好,这只是一个理解方式罢了. 思想简述 顾名思义,这个算法是处 ...

  2. 1569: Wet Tiles

    Description Alice owns a construction company in the town of Norainia, famous for its unusually dry ...

  3. ZeptoLab Code Rush 2015 B. Om Nom and Dark Park

    Om Nom is the main character of a game "Cut the Rope". He is a bright little monster who l ...

  4. 洛谷P1628合并序列【模板】(Trie+dfs)

    很久之前写的题了,当时不知道怎么dfs所以卡了一段时间,^_^ 题解:由于题目给了一大堆字符串,所以首先考虑应该可以建树,之后找到T所在的位置,对T所在的位置dfs就行了 代码: 1 #include ...

  5. AtCoder Beginner Contest 173 E - Multiplication 4 (思维)

    题意:有\(n\)个数,从中选\(k\)个数累乘,求最大的乘积\((mod\ 10^9+7)\). 题解: 1.假如全是负数,并且选奇数个,那么从小到大选. 2.否则,考虑当前状态,假如\(k\)是奇 ...

  6. 【一天一个基础系列】- java之泛型篇

    简介 说起各种高级语言,不得不谈泛型,当我们在使用java集合的时候,会发现集合有个缺点:把一个对象"丢进"集合之后,集合就会"忘记"这个对象的数据类型,当再次 ...

  7. 设计模式(二十一)——解释器模式(Spring 框架中SpelExpressionParser源码分析)

    1 四则运算问题 通过解释器模式来实现四则运算,如计算 a+b-c 的值,具体要求 1) 先输入表达式的形式,比如 a+b+c-d+e,  要求表达式的字母不能重复 2) 在分别输入 a ,b, c, ...

  8. Java解决Hash(散列)冲突的四种方法--开放地址法(线性探测,二次探测,伪随机探测)、链地址法、再哈希、建立公共溢出区

    最近时间有点紧,暂时先放参考链接了,待有时间在总结一下: 查了好多,这几篇博客写的真心好,互有优缺点,大家一个一个看就会明白了: 参考 1. 先看这个明白拉链法(链地址法),这个带源码,很好看懂,只不 ...

  9. QUIC协议文档翻译——什么是QUIC

    原文地址https://docs.google.com/document/d/1gY9-YNDNAB1eip-RTPbqphgySwSNSDHLq9D5Bty4FSU/edit QUIC是一个谷歌提出 ...

  10. github gist 无法访问

    转自这里 以管理员身份在hosts文件: Windows: C:\Windows\System32\drivers\etc Ubuntu: /etc/hosts 添加: 192.30.253.118 ...