redis缓存击穿与内存淘汰策略无直接因果关系:击穿源于热点key过期瞬间的高并发穿透,与内存使用量无关;淘汰策略仅在maxmemory触达后生效,用于解决内存不足问题,选错策略(如volatile-ttl、random)可能加剧击穿风险。

Redis缓存击穿和内存淘汰策略没有直接因果关系,但它们可能在高并发场景下被同时触发、相互干扰。
缓存击穿发生时,Redis根本没走到淘汰那步
缓存击穿的核心是:一个热点 key 到期瞬间,大量请求同时发现缓存缺失,全部打到数据库。这个过程发生在「缓存未命中 → 查询 DB → 写回缓存」的业务逻辑里,和 Redis 内存是否满、是否触发 maxmemory-policy 完全无关。
- 击穿只依赖
EXPIRE或SET key value EX 60这类过期设置,跟内存使用量无关 - 即使你配置了
allkeys-lru,只要内存没满,Redis 就不会主动删任何 key —— 所以到期 key 不会因“淘汰”提前消失,而是按 TTL 精确失效 - 真正危险的是:多个请求几乎同时发现 key 过期,又没加锁,结果重复查 DB + 重复写缓存
内存淘汰策略影响的是“非热点但占内存”的数据
淘汰策略只在 maxmemory 被触及后才生效,它解决的是「内存不够用」问题,不是「热点 key 失效」问题。选错策略反而会让击穿更难处理:
Redis 缓存和数据结构管理技能。通过自然语言操作 Redis,支持 String、Hash、List、Set、ZSet、Stream 等数据结构操作。当用户提到 Redis、缓存、消息队列、会话存储时使用此技能。
- 用
volatile-ttl?它会优先删快过期的 key —— 如果你给热点 key 设置了短 TTL,它可能比冷数据更早被删,加剧击穿频率 - 用
noeviction(默认)?内存满时直接报错(error) OOM command not allowed when used memory > 'maxmemory'.,写缓存失败,导致后续请求永远查不到,变成“伪击穿” - 用
allkeys-lfu?如果热点 key 访问频次高,它大概率会被保留;但 LFU 统计有延迟,刚重建的缓存可能因访问次数少而被误删
怎么配淘汰策略才不拖缓存击穿的后腿
关键不是“防击穿”,而是避免淘汰策略干扰你的缓存稳定性:
- 对纯缓存场景(如 session、临时 token),优先选
volatile-lru:只淘汰带过期时间的 key,不影响永不过期的热点数据 - 如果必须混存持久数据和缓存数据,用
allkeys-lru,但务必确保热点 key 的EXPIRE时间足够长(比如 24h+),避免被 LRU 误判为“冷数据” - 绝对不要用
volatile-random或allkeys-random:随机删 key 可能刚写入的热点缓存就被干掉,等于主动制造击穿 - 检查
INFO memory中的mem_used_human和maxmemory_human,确保内存余量 ≥ 20%,给 LRU/LFU 统计留出缓冲空间
真正该盯住的两个配置项
击穿问题最终要靠应用层控制,但这两个 Redis 配置会放大或缓解它的影响:
-
maxmemory:设太小会导致频繁触发淘汰,间接增加 key 波动;建议设为物理内存的 40%~60% -
maxmemory-policy:别只看名字,要结合你 key 的过期习惯 —— 比如大量用PEXPIRE设毫秒级 TTL,volatile-ttl就比volatile-lru更危险
复杂点在于:LRU/LFU 在 Redis 里是近似算法,采样数(maxmemory-samples 默认 5)越小,淘汰越随机;如果你的热点 key 刚重建完就遭遇采样,可能被当成“最近没访问”直接踢掉 —— 这种细节,比选哪个策略更值得花时间验证。










