高阶数据结构学习——LRU Cache

文章目录

  • 1、了解LRU Cache(Least Recently Used缩写)
  • 2、代码实现


1、了解LRU Cache(Least Recently Used缩写)

Cache是缓存,在磁盘和内存之间,内存和寄存器之间都存在,CPU和内存之间存在三级缓存,是一个三层结构。缓存用于两个速度不一致的硬件之间,提高效率用。缓存空间有限,满了以后,新数据要进入,旧数据应当怎么办?操作系统中有个热数据概念,意思是经常被使用的数据,可能放进缓存就被拿出来,再次放进后又被拿出来使用,对应的,也有很少被使用的,也就是LRU的意思,缓存满了后,新数据进来,这些很少被使用的就出去。

设计一个LRU Cache不难,设计一个高效的,任意操作都是O(1)的LRU Cache不简单,但只有这样才能满足要求。LRU Cache最主要的操作是get和put,这两个接口必须以O(1)的时间复杂度进行。

2、代码实现

看一个题

146. LRU 缓存

在这里插入图片描述
在这里插入图片描述

看在不在,可以看地址是否在缓存中。整个操作有查找,更新,新增。虽然可以用unordered_map作为缓存,做到查找,更新都O(1),但如何找到LRU?这涉及到顺序问题,还有时间问题,这里的解决办法就是用vector或list来控制LRU,比如list,在这个list里,让处于尾部就是最久未被使用的,用一个数据就把它提到头部,list<pair<int, int>> _LRUList。但这两个结合还是做不到O(1)。因为更新时无法做到O(1),更新时可以直接修改map里的数据,但在list中更新时需要先找到这个数据再放到头部,所以不是O(1)。

以上问题的解决办法是找到key时,就同时找到key对应存储数据在list中的位置。把map中value的类型换成list的迭代器,这样map[key]中存的就是一个指针,指向list中的对应的元素,如果要使用这个数据时就用指针把它拿出来,然后头插即可。

private:typedef list<pair<int, int>>::iterator LtIter;unordered_map<int, LtIter> _hashMap;list<pair<int, int>> _LRUList;
class LRUCache {
public:LRUCache(int capacity) :_capacity(capacity){}int get(int key) {auto ret = _hashMap.find(key);if(ret != _hashMap.end()){//更新key对应值的位置LtIter it = ret->second;//方案1: erase + push_front 更新迭代器,原迭代器失效//方案2: list的splice接口可以转移节点_LRUList.splice(_LRUList.begin(), _LRUList, it);return ret->second->second;//第一个second对应迭代器,第二个second对应list的pair}else{return -1;}}void put(int key, int value) {//1、新增//2、更新auto ret = _hashMap.find(key);if(ret == _hashMap.end())//新增{if(_capacity == _hashMap.size()){pair<int, int> back = _LRUList.back();_hashMap.erase(back.first);_LRUList.pop_back();  }_LRUList.push_front(make_pair(key, value));_hashMap[key] = _LRUList.begin();}else//更新{LtIter it = ret->second;it->second = value;_LRUList.splice(_LRUList.begin(), _LRUList, it);}}
private:typedef list<pair<int, int>>::iterator LtIter;unordered_map<int, LtIter> _hashMap;list<pair<int, int>> _LRUList;size_t _capacity;
};

结束。

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

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

相关文章

基于PyTorch的中文情绪分析器设计与开发

收藏和点赞&#xff0c;您的关注是我创作的动力 文章目录 概要 一、相关基础理论2.1 主流深度学习框架2.2 神经网络2.2.1 神经网络基础 二、中文情感分类模型构建3.1 开发环境3.2 数据部分3.3 文本特征提取3.3.1、过滤标点符号3.3.2 中文分词、单词过滤 三 运行结果与分析五 结…

2,OpenCV函数解析

1&#xff0c;imread函数&#xff1a;图片读取 CV_EXPORTS_W Mat imread( const String& filename, int flags IMREAD_COLOR );//参数1(filename)&#xff1a;文件地址 //参数2(flags):读取标志注:ImreadModes&#xff0c;参数2(flags)枚举定义 enum ImreadModes {IMREA…

快速批量重命名:高效修改文件名并转换为大写扩展名

在文件管理中&#xff0c;批量重命名文件是一个常见的需求。通过快速批量重命名&#xff0c;我们可以高效地修改文件名并将扩展字母转换为大写形式。这样做不仅可以提高文件的可读性&#xff0c;还可以更好地组织和管理文件。用云炫文件管理器可以快速批量重命名&#xff0c;能…

k8s之pod进阶---资源限制与探针

目录 一、资源限制 二、探针&#xff08;健康检查&#xff09; 2.1 含义 2.2 探针的三种规则 2.3 probe支持三种检查方法 2.4 探针的示例 1、存活探针&#xff1a;livenessProbe &#xff08;1&#xff09;exec方式 &#xff08;2&#xff09;httpGet方式 &#xff08;…

如何使用ps制作ico图标文件

如何使用ps制作ico图标文件 Chapter1 如何使用ps制作ico图标文件Chapter2 ICOFormat.8bi&#xff08;Photoshop Ico、Cur插件&#xff09;的下载使用1. ICOFormat.8bi的作用2. ICOFormat.8bi使用 Chapter3 ps手机计算机图标教程,手绘设计精美手机APP软件图标的PS教程步骤 01 制…

目标检测中常见指标 - mAP

文章目录 1. 评价指标2. 计算示例3. COCO评价指标 1. 评价指标 在目标检测领域&#xff0c;比较常用的两个公开数据集&#xff1a;pascal voc和coco。 目标检测与图像分类明显差距是很大的&#xff0c;在图像分类中&#xff0c;我们通常是统计在验证集当中&#xff0c;分类正…

maven配置多仓库

配置多仓库不要用mirror&#xff0c;要用profile。 先将mirror全注释掉。 <?xml version"1.0" encoding"UTF-8"?> <settings xmlns"http://maven.apache.org/SETTINGS/1.0.0"xmlns:xsi"http://www.w3.org/2001/XMLSchema-insta…

代码随想录图论并查集 第七天 | 685.冗余连接II

代码随想录图论并查集 第七天 | 685.冗余连接II 一、685.冗余连接II 题目链接&#xff1a;https://leetcode.cn/problems/redundant-connection-ii/ 思路&#xff1a;684.冗余连接中是连通且无环的无向图可直接使用并查集模板&#xff0c;如果想判断集合中是否有环&#xff0…

佳易王定制开发流水线商品标签自动打印软件,打印格式可定制

佳易王定制开发流水线商品标签自动打印软件&#xff0c;打印格式可以定制 软件特色&#xff1a; 定制试用商品标签打印管理V16.0&#xff0c;打印标签可以自动计算到期日期和品控日期&#xff0c;并打印品名、包装规格、生产日期、到期日期、储存条件、生产包装、品控日期等信…

阿里测试8年,肝到P8只剩他了····

在阿里工作了8年&#xff0c;工作压力大&#xff0c;节奏快&#xff0c;但是从技术上确实得到了成长&#xff0c;尤其是当你维护与大促相关的系统的时候&#xff0c;熬到P7也费了不少心思&#xff0c;小编也是个爱学习的人&#xff0c;把这几年的工作经验整理成了一份完整的笔记…

Spring Cloud智慧工地源码,利用计算机技术、互联网、物联网、云计算、大数据等新一代信息技术开发,微服务架构

智慧工地系统充分利用计算机技术、互联网、物联网、云计算、大数据等新一代信息技术&#xff0c;以PC端&#xff0c;移动端&#xff0c;设备端三位一体的管控方式为企业现场工程管理提供了先进的技术手段。让劳务、设备、物料、安全、环境、能源、资料、计划、质量、视频监控等…

Python自动化运维监控——批量监听页面发邮件(自由配置ini文件+smtplib)

一、程序样式 1.listen.ini配置文件 2.监控页面 3.日志 二、核心点 smtplib库&#xff1a;这里使用了smtp.qq.com与smtp.163.com两个发送邮件的地址&#xff0c;使用邮箱用户名与授权码来实现登录&#xff0c;端口都使用465&#xff0c;最后抛出异常&#xff0c;finally里…

springboot的请求与响应

一&#xff0c;简单参数 Get请求&#xff1a;只需要在postman中的Params参数与方法中的形参一致就可以Post请求与Get方法一致只需要在 如果参数名不一致--通过RequestParam中的value属性执行请求参数名 RequestParam(name "name",required false) //表示name参数不是…

如何设计一个mysql的统计分析表?

在设计这样的MySQL统计分析表时&#xff0c;首先要明确所要收集的数据。我们至少需要以下几方面的数据&#xff1a; 病例ID&#xff0c;用于唯一标识每个病例。地区&#xff0c;即病例发生的地理位置。人群类别&#xff0c;比如儿童、青少年、成年人、老年人等。食源性级别&am…

react 性能优化之useCallback和useMemo的区别

useCallback缓存函数优化子组件减少渲染useMemo缓存返回值优化当前组件减少渲染

【CesiumJS】(1)Hello world

介绍 Cesium 起源于2011年&#xff0c;初衷是航空软件公司(Analytical Graphics, Inc.)的一个团队要制作世界上最准确、性能最高且具有时间动态性的虚拟地球。取名"Cesium"是因为元素铯Cesium让原子钟非常准确&#xff08;1967年&#xff0c;人们依据铯原子的振动而对…

【面经】什么是行锁/表锁,什么时候锁行/锁表

什么是行锁/表锁 行锁是指在事务执行期间&#xff0c;仅对数据表中的某一行(或某几行)加锁&#xff0c;其他行不受影响。 行锁适用于需要对表中部分数据进行修改或查询的情况。 它可以防止多个事务同时修改同一行数据&#xff0c;从而保证数据的一致性和完整性。 在大多数情况…

【实战Flask API项目指南】之三 路由和视图函数

实战Flask API项目指南之 路由和视图函数 本系列文章将带你深入探索实战Flask API项目指南&#xff0c;通过跟随小菜的学习之旅&#xff0c;你将逐步掌握 Flask 在实际项目中的应用。让我们一起踏上这个精彩的学习之旅吧&#xff01; 前言 当小菜踏入Flask后端开发的世界时&…

柯桥俄语考级培训,俄语专八如何备考

1.用好真题 真题一共分为&#xff1a;口语表述、听力、词汇语法句法、文学常识、国情、阅读理解、俄汉互译、作文等部分。 第一&#xff0c;要自己动手做真题&#xff0c;然后对答案&#xff0c;看错题错在什么地方&#xff0c;还有哪些知识点是盲区。 第二&#xff0c;分析每…

Android GB28181历史视音频回放

作为GB28181安卓客户端&#xff0c;实时视音频点播是必须支持的功能&#xff0c;对于历史视音频回放功能&#xff0c;不支持的话可以从设备上拷贝录像文件再播放&#xff0c;但有些场景没法拷贝&#xff0c;安卓支持回放还是需要的。 历史视音频的回放和实时视音频点播信令上很…