bigywater.tech
Redis · 23

LFU 淘汰算法

用allkeys-lfu策略,对比400个高频访问的key和400个从不访问的key,看内存淘汰时访问频率起了多大作用。

87.5% vs 26.75%
高频key与冷key的幸存率对比
对数压缩计数
OBJECT FREQ反映的访问频率
历史频率优先
LFU不看最近,只看用得多不多

做的事:两组key,一组高频访问,一组完全不碰

LFU(Least Frequently Used)按的访问次数决定谁先被淘汰,不是按最近有没有访问过。

操作CONFIG SET maxmemory-policy allkeys-lfu CONFIG SET maxmemory 3mb SET 400个hot_*,然后各GET 50次 SET 400个cold_*,完全不访问 继续插入更多key,触发内存淘汰

验证:高频访问的key,幸存率高出3倍多

同样是400个key,访问模式完全不同,淘汰结果差很多。

结果evicted_keys: 742 hot_(高频访问50次) 幸存: 350 / 400 (87.5%) cold_(从未访问) 幸存: 107 / 400 (26.75%) OBJECT FREQ hot_0 → :8 OBJECT FREQ cold_0 → :5

结果很清楚:hot_* 幸存率87.5%,cold_* 幸存率只有26.75%,差了3倍多。OBJECT FREQ 显示hot key的频率计数(8)比cold key(5)更高——注意这个计数是对数压缩过的(不是访问50次就直接显示50),Redis用了一种"访问越多、计数增长越慢"的算法,防止频率计数器无限增长占用过多空间,同时保证老热key不会因为计数太大而永远淘汰不掉冷key(还内置了衰减机制,长期不访问的key频率会慢慢降下来)。

这就是LFU的核心思路:淘汰的依据是"这个key历史上到底被用了多少次",而不是LRU那种"最近一次用是什么时候"。对于存在"热点数据反复被访问,但偶尔有一段时间没被点到"的场景(比如社交媒体的热门内容),LFU比LRU更不容易误伤真正重要的热数据。

分步演示:访问频率是怎么影响淘汰结果的

每一步都是本文上面用redis-cli和redis-py跑出来的原始结果。

LFU按访问频率决定谁先被淘汰
这一步新验证的结果

    本文用到的工具

    • 本机 Redis 8.10.1 单节点,maxmemory=3MB
    • CONFIG SET maxmemory-policy allkeys-lfu / OBJECT FREQ:验证按频率淘汰
    京ICP备2026067502号-1京公网安备11010502063487号