leetcode 面试150之 156.LUR 缓存

请你设计并实现一个满足  LRU (最近最少使用) 缓存 约束的数据结构。

实现 LRUCache 类:

  • LRUCache(int capacity) 以 正整数 作为容量 capacity 初始化 LRU 缓存
  • int get(int key) 如果关键字 key 存在于缓存中,则返回关键字的值,否则返回 -1 。
  • void put(int key, int value) 如果关键字 key 已经存在,则变更其数据值 value ;如果不存在,则向缓存中插入该组 key-value 。如果插入操作导致关键字数量超过 capacity ,则应该 逐出 最久未使用的关键字。

函数 get 和 put 必须以 O(1) 的平均时间复杂度运行。

题目重点:O(1)实现查找和删除

O(1)查找我们可以通过unordered_map底层哈希表来实现
这里我们如果缓存满了还得删除最久未使用关键字 ,所以我们得使用一个O(1)维护的“使用队列”,数组我们无法实现O(1)删除,而双向链表能实现O(1)删除,但是无法实现O(1)查询

所以我们这里用到了unordered_map<int,listnode*>映射为listnode*,通过map去实现O(1)查询
而listnode*双向链表实现O(1)插入和删除

起初我并未想到用双向链表而是用deque去维护“使用队列”,后者在维护队列无法做到O(1),包超时的

上代码:

class LRUCache {
public:struct listnode{int key;int val;listnode* pre;listnode* next;listnode(int k,int v):key(k),val(v),pre(nullptr),next(nullptr){}};int max_;                          //最大空间listnode* head;                    //头哨兵节点listnode* tail;                    //尾哨兵节点unordered_map<int,listnode*> dp;   //精华//初始化    LRUCache(int capacity) {max_=capacity;head=new listnode(0,0);tail=new listnode(0,0);head->next=tail;tail->pre=head;}//双向链表头插法 将处理的node节点 使用优先级提高void addnode(listnode* node){node->next=head->next;head->next->pre=node;head->next=node;node->pre=head;}//断开node节点 并未delete  void remove_node(listnode* node){node->pre->next=node->next;node->next->pre=node->pre;}//查询数据int get(int key) {if(dp.count(key))          //查询成功 提高该节点的“使用队列”优先级{remove_node(dp[key]);addnode(dp[key]);return dp[key]->val;}else return -1;}//插入数据void put(int key, int value) {if(dp.count(key)){dp[key]->val=value;    //已经存在   更新val后,取走节点后插入头  提高优先级remove_node(dp[key]);addnode(dp[key]);}//key不存在else{if(max_==dp.size())          //空间已满  删除优先级低节点 也就是 tail->pre{listnode* temp=tail->pre;remove_node(temp);dp.erase(temp->key);delete temp;               //释放内存}//无论空间是否够 都需要插入这个key节点listnode* node=new listnode(key,value); addnode(node);dp.insert({key,node});}}
};/*** Your LRUCache object will be instantiated and called as such:* LRUCache* obj = new LRUCache(capacity);* int param_1 = obj->get(key);* obj->put(key,value);*/

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/61856.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

HTTP工作原理

HTTP协议工作于客户端/服务端架构上。浏览器作为HTTP客户端通过URL向HTTP服务端即WEB服务器发送所有请求。 首先客户端与服务器需要建立连接。只要单击某个超链接&#xff0c;HTTP就开始工作。 建立连接后&#xff0c;客户端发送一个请求给服务器&#xff0c;请求方式的格式为&…

Android Studio更改项目使用的JDK

一、吐槽 过去&#xff0c;在安卓项目中配置JDK和Gradle的过程非常直观&#xff0c;只需要进入Android Studio的File菜单中的Project Structure即可进行设置&#xff0c;十分方便。 原本可以在这修改JDK: 但大家都知道&#xff0c;Android Studio的狗屎性能&#xff0c;再加…

字节青训营开课啦

系列文章目录 文章目录 系列文章目录一、字节青训营是什么&#xff1f;二、你将获得三、入营条件四、课程简介1.前端2.后端3.大数据 五、报名 一、字节青训营是什么&#xff1f; 青训营是字节跳动技术团队发起的技术系列培训&人才选拔项目&#xff1b;面向高校在校生&…

医药企业的终端市场营销策略

近年来&#xff0c;随着医药行业的快速发展&#xff0c;终端市场逐渐成为企业竞争的关键领域。在政策趋严、市场环境变化以及数字化转型的大背景下&#xff0c;医药企业如何在终端市场中立于不败之地&#xff1f;本文结合我们在医药数字化领域的经验&#xff0c;为大家剖析终端…

经验笔记:远端仓库和本地仓库之间的连接(以Gitee为例)

经验笔记&#xff1a;远端仓库和本地仓库之间的连接 方法一&#xff1a;先创建远端仓库&#xff0c;再克隆到本地 创建远端仓库 登录到你的Git托管平台&#xff08;如Gitee、GitHub、GitLab、Bitbucket等&#xff09;。点击“New Repository”或类似按钮&#xff0c;创建一个新…

重构代码之将单向关联转换为双向关联

将单向关联转换为双向关联 旨在将类之间的单向关联转换为双向关联。这通常用于改善对象模型的可访问性和灵活性&#xff0c;尤其是在涉及复杂关系的领域模型中。它适用于对象关系之间存在单向引用&#xff0c;但业务逻辑要求这些对象能够相互访问和更新的场景。 一、什么是单向…

养老院管理系统+小程序项目需求分析文档

智慧综合养老服务平台是以业务为牵引、场景为驱动&#xff0c;围绕“老人”业务域&#xff0c;持续沉淀和打磨形成适应不同养老业务发展需要的业务能力&#xff0c;推动业务模式升级&#xff0c;为养老服务提供数字化解决方案&#xff0c;并依托实体站点与养老机构实现线上线下…

迄今为止的排序算法总结

迄今为止的排序算法总结 7.10 迄今为止的排序算法总结复杂度和稳定性时间复杂度测试程序sortAlgorithm.hsortAlgorithm.cpptest.cpp 时间复杂度测试结果 7.10 迄今为止的排序算法总结 复杂度和稳定性 排序算法平均情况最好情况最坏情况稳定性空间复杂度选择排序O(n^2)O(n^2)O…

SpringBoot集成ES(ElasticSearch)

1.导入依赖 <dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-data-elasticsearch</artifactId> </dependency>导入依赖后&#xff0c;注意在依赖中查看对应的版本是否与本机ES对应 2.创建配置并…

FEM位移边界条件的处理

在有限元分析中&#xff0c;处理唯一约束&#xff08;如位移边界条件或特定的自由度被固定&#xff09;&#xff0c;常见的方法包括以下几种。每种方法的特点和适用场景有所不同&#xff0c;具体选择取决于问题性质和数值求解需求。 直接代入法 置大数法 置1法 拉格朗日乘子法…

ant-design-vue中table某一列进行合并

ant-design-vue中table某一列进行合并 1、在colums中配置自定义渲染 {title: 区域,dataIndex: cityName,key: cityName,align: center,width: 120,customCell: (record, rowIndex, column) > {return {rowSpan: record.rowSpan}} },2、处理请求来的数据 tableData.dataSo…

MySQL高级(五):事务

概念 事务是数据库管理系统中用于保证数据一致性和完整性的重要机制。它允许将一组操作视为一个整体&#xff0c;要么全部执行&#xff0c;要么全部回滚&#xff0c;以确保数据的正确性。 事务的特性&#xff08;ACID&#xff09; 原子性&#xff08;Atomicity&#xff09; …

Flutter:flutter_screenutil屏幕适配

1、安装flutter_screenutil flutter_screenutil: ^5.9.32、main入口修改 // 新增 ScreenUtilInit()class MyApp extends StatelessWidget {const MyApp({Key? key}) :super(key: key);overrideWidget build(BuildContext context) {return ScreenUtilInit(designSize: const S…

数据结构之二:表

顺序表代码&#xff1a;SData/SqList/SeqList.h Hera_Yc/bit_C_学习 - 码云 - 开源中国 链表相关代码&#xff1a;SData/ListLink/main.c Hera_Yc/bit_C_学习 - 码云 - 开源中国 本文主要讲解的是线性表&#xff08;逻辑线性&#xff09;&#xff0c;对于非线性表不做补充。…

《Python基础》之循环结构

目录 简介 一、for循环 1、基本语法与作用 2、使用 range() 函数配合 for 循环 3、嵌套的for循环 二、while循环 1、基本语法与作用 2、while 循环嵌套 &#xff08;1&#xff09;、while循环与while循环嵌套 &#xff08;2&#xff09;、while循环与for循环嵌套 简介 …

Android开发实战班 - 数据持久化 - 数据加密与安全

在 Android 应用开发中&#xff0c;数据安全至关重要&#xff0c;尤其是在处理敏感信息&#xff08;如用户密码、支付信息、个人隐私数据等&#xff09;时。数据加密是保护数据安全的重要手段&#xff0c;可以有效防止数据泄露、篡改和未经授权的访问。本章节将介绍 Android 开…

【jvm】AOT编译器

目录 1. 说明2. AOT编译器的引入与基本概念3. AOT编译器的工作原理与流程4. 优点5. 缺点6. AOT编译器与JIT编译器的比较6.1 JIT编译器6.2 AOT编译器 7.AOT编译器的应用场景与限制 1. 说明 1.JVM&#xff08;Java虚拟机&#xff09;中的AOT&#xff08;Ahead Of Time&#xff0…

IOC/异步编程

文章目录 项目地址一、IOC 控制反转1.1 先看一个不使用IOC的例子1.2 使用IOC实现1.2.1 依赖注入1.2.2 IOC容器是什么 1.2.3 使用反射给属性赋值1.2.4 通过PropertyInfo[]批量获取对象1.2.5 使用type完成依赖注入1.2.6 使用特性进行对象过滤1.2.6完整代码 项目地址 教程作者&am…

基于LiteFlow的风控系统指标版本控制

个人博客&#xff1a;无奈何杨&#xff08;wnhyang&#xff09; 个人语雀&#xff1a;wnhyang 共享语雀&#xff1a;在线知识共享 Github&#xff1a;wnhyang - Overview 更新日志 最近关于https://github.com/wnhyang/coolGuard此项目更新了如下内容&#xff1a;https://g…

Mysql中的 TEXT 和 BLOB 解析

&#x1f680; 博主介绍&#xff1a;大家好&#xff0c;我是无休居士&#xff01;一枚任职于一线Top3互联网大厂的Java开发工程师&#xff01; &#x1f680; &#x1f31f; 在这里&#xff0c;你将找到通往Java技术大门的钥匙。作为一个爱敲代码技术人&#xff0c;我不仅热衷…