Redis Key 过期后会立刻删除吗?过期删除与内存淘汰策略详解

Redis 里的 key 可以设置过期时间,但 key 到期并不意味着会被立刻删除。Redis 需要在 CPU 成本和内存释放之间做平衡,所以采用的是:惰性删除 + 定期删除

当内存真的不够用时,Redis 还会根据内存淘汰策略删除一部分 key。

这篇把两个问题放在一起讲:

  1. key 过期后怎么删除?
  2. 内存满了以后怎么淘汰?

一、惰性删除:访问时才检查

惰性删除的意思是:设置了过期时间后,Redis 不会一直盯着这个 key。只有当客户端访问这个 key 时,Redis 才检查它是否过期。
未过期
已过期
客户端访问 key
key 是否过期
返回 value
删除 key
返回空

优点是对 CPU 友好,因为 Redis 不需要为每个过期 key 立刻做检查。

缺点是对内存不友好:如果一个 key 已经过期,但再也没人访问它,它可能会继续占在内存里。

二、定期删除:周期性抽样清理

为了避免过期 key 一直占内存,Redis 会定期抽取一部分 key 检查并删除过期数据。


定时任务
随机抽取部分 key
是否过期
删除
保留

课件里提到定期清理有两种模式:

模式 特点
SLOW 定时任务,默认 10hz,每次不超过 25ms
FAST 执行频率不固定,两次间隔不低于 2ms,每次不超过 1ms

定期删除的优点是可以主动释放内存,同时通过限制时长和频率减少对 CPU 的影响。缺点是很难精确控制执行频率:太频繁会影响 CPU,太少又会让过期 key 占用内存。

所以 Redis 最终采用组合策略:

text 复制代码
Redis 过期删除策略 = 惰性删除 + 定期删除

三、内存满了怎么办?

过期删除解决的是"已经设置 TTL 的 key 到期后怎么清理"。但如果 Redis 内存已经满了,新的写入进来怎么办?

这就涉及内存淘汰策略。Redis 会按照配置的规则选择一部分 key 删除。

四、Redis 的 8 种淘汰策略

策略 作用范围 淘汰规则
noeviction 不淘汰 内存不足时新写入直接报错
volatile-ttl 设置了 TTL 的 key 剩余 TTL 越小越先淘汰
allkeys-random 全体 key 随机淘汰
volatile-random 设置了 TTL 的 key 随机淘汰
allkeys-lru 全体 key 淘汰最近最少使用
volatile-lru 设置了 TTL 的 key 淘汰最近最少使用
allkeys-lfu 全体 key 淘汰访问频率最低
volatile-lfu 设置了 TTL 的 key 淘汰访问频率最低

默认策略是 noeviction,也就是内存不足时不删除任何数据,新写入会报错。

五、LRU 和 LFU 的区别

LRU 是 Least Recently Used,最近最少使用。它看的是"多久没被访问过"。

text 复制代码
当前时间 - 最后一次访问时间 = 越大越优先淘汰

LFU 是 Least Frequently Used,最少频率使用。它看的是"访问次数多不多"。

text 复制代码
访问频率越低,淘汰优先级越高

简单理解:LRU 更关注最近有没有用,LFU 更关注长期用得多不多。

六、开发中怎么选?

业务特点 推荐策略
有明显冷热数据 allkeys-lru
访问频率差别不大 allkeys-random
有置顶数据不能淘汰 volatile-lru,置顶 key 不设置 TTL
短时高频访问明显 allkeys-lfu 或 volatile-lfu
不允许 Redis 自动删数据 noeviction

面试里经常会问:"数据库有 1000 万数据,Redis 只能缓存 20 万,怎么保证 Redis 里都是热点数据?"

可以回答:使用 allkeys-lruallkeys-lfu,让 Redis 自动淘汰不常访问的数据,留下更热的数据。

最后总结一句:

Redis key 过期不会立刻删除,而是惰性删除和定期删除配合;内存不够时才会触发淘汰策略。平时开发最常用的是 allkeys-lru,能让最近常访问的数据尽量留在缓存里。

相关推荐
咖啡八杯5 小时前
GoF设计模式——策略模式
java·后端·spring·设计模式
用户1285261160212 小时前
我把祖传Java项目重构后,接口响应从3s砍到了200ms,只改了这几行代码
java
Linsk13 小时前
组件 = 模板 + 业务逻辑
java·前端·vue.js
星沉远浦13 小时前
用Gemini高效解决Java代码报错难以定位的问题
java
用户2986985301417 小时前
Word 文档字符级格式化:Java 实现方案详解
java·后端
笨鸟飞不快17 小时前
从单个服务到集群:一次完整的性能排查复盘
java·前端
荣码18 小时前
用Streamlit给AI应用套个界面,10行代码出Web页面
java·python
SamDeepThinking18 小时前
Java微服务练习方式
java·后端·微服务
朦胧之1 天前
AI 编程-老项目改造篇
java·前端·后端
程序猿大帅1 天前
别再只当调包侠了:用 Spring AI 落地 Function Calling,我被大模型硬生生砸出了三个大坑
java