Redis 的 Key 过期删除策略,可以说是其内存管理中最有趣、也最常被问到的部分。它并不是靠单一机制来清理过期数据,而是有一套组合拳:被动删除和主动删除双管齐下。这套设计到底是怎么运作的?我们一步步拆开看。 1. 被动删除(惰性删除 - Lazy Expiration) 工作原理 说白了就是:你
Redis 的 Key 过期删除策略,可以说是其内存管理中最有趣、也最常被问到的部分。它并不是靠单一机制来清理过期数据,而是有一套组合拳:被动删除和主动删除双管齐下。这套设计到底是怎么运作的?我们一步步拆开看。
说白了就是:你不找我,我就不删。当客户端发起请求、访问某个 Key 时,Redis 会先检查一下这个 Key 是否已经过期。如果过期了,当场删除,然后返回 nil——就像它从来没存在过一样。如果还活着,那就正常返回数据。
长期稳定更新的攒劲资源: >>>点此立即查看<<<
对 CPU 极其友好。只有在被访问的那一刻才消耗资源,其他时间完全不动。简单直接,不影响那些无人问津的 Key。
对内存不太友好。如果某些过期 Key 永远没人访问,它们就会一直赖在内存里不走。极端情况下,可能造成内存浪费甚至是“泄露”。
既然光靠被动删除不靠谱,Redis 还会主动出击。它以一个固定的频率(默认每秒 10 次)执行以下步骤:
对应的配置参数(在 redis.conf 中):
# 每秒执行过期扫描的次数(默认 10)
hz 10
# 每次扫描的 CPU 时间百分比上限(默认 25%)
# 实际上每次扫描最多 25ms(1000ms / hz * 25%)
能在内存中减少过期 Key 的堆积,在 CPU 消耗和内存占用之间找到一个不错的平衡点。
不是实时的,可能存在某个 Key 已经过期几分钟了,但还没被扫描到的情况。而且,定期执行本身也增加了一定的 CPU 开销。
如果说前两种策略是“日常保洁”,那当内存真的撑不住了——也就是达到了 maxmemory 限制时——Redis 就会启动最后防线:根据你配置的淘汰策略来强行腾空间。
# 内存限制(默认不限制)
maxmemory
# 淘汰策略
maxmemory-policy
可选的淘汰策略有这么几种:
| 策略 | 描述 | 适用场景 |
|---|---|---|
| noeviction | 不淘汰,直接返回错误 | 数据绝对不能丢失 |
| allkeys-lru | 从所有 Key 中选出最近最少使用的淘汰 | 需要缓存效果 |
| volatile-lru | 从设置了过期时间的 Key 中选出最近最少使用的淘汰 | 混合使用 |
| allkeys-random | 从所有 Key 中随机淘汰 | 所有 Key 同等重要 |
| volatile-random | 从设置了过期时间的 Key 中随机淘汰 | 混合使用 |
| volatile-ttl | 淘汰即将过期的 Key(TTL 最小的) | 优先保留新数据 |
| allkeys-lfu | 从所有 Key 中选出最不经常使用的淘汰(4.0+ 版本) | 访问频率更重要 |
| volatile-lfu | 从设置了过期时间的 Key 中选出最不经常使用的淘汰(4.0+ 版本) | 混合使用 |

想知道系统中有多少 Key 已被清理?可以这样查:
redis-cli info stats | grep expired_keys
hz 值决定了主动扫描的频率。
hz 100 # 更高频率,清理更及时,但 CPU 消耗也更高
hz 1 # 更低频率,CPU 友好,但可能导致过期 Key 堆积
这是一个非常经典的优化点。如果大批 Key 在同一秒过期,会导致 Redis 在那一瞬间的 CPU 飙升。通常的做法是加入随机偏移量:
# 不好的做法:同时设置相同过期时间
for i in range(100000):
redis.set(f"key:{i}", "data", ex=3600)
# 好的做法:添加随机偏移
for i in range(100000):
redis.set(f"key:{i}", "data", ex=3600 + random.randint(0, 300))
- RDB:生成快照时,过期的 Key 不会被保存到文件中。
- AOF:当 Key 过期时,Redis 会追加一条 DEL 命令到 AOF 文件里。
- 主节点删除过期 Key 后,会主动向从节点发送一条 DEL 命令。
- 从节点没有自主删除过期 Key 的权限,完全听命于主节点的指令。
- 每个节点独立管理自己的过期 Key。
- 当槽位发生迁移时,Key 的过期信息也会一并迁移到目标节点。
Redis 的过期删除策略,本质上就是一套 惰性删除 + 定期删除 的组合拳:
这套机制在 CPU 使用率、内存效率和实现复杂性之间,取得了相当不错的平衡。也正是因此,Redis 才能在高并发场景下流畅地处理海量带有过期时间的 Key。
侠游戏发布此文仅为了传递信息,不代表侠游戏网站认同其观点或证实其描述