Redis 过期策略 和 回收策略

过期策略

1、惰性策略

惰性策略就是在客户端访问这个 key 的时候,redis 对 key 的过期时间进行检查,如果过期了就立即删除。

2、定时删除策略

Redis 默认会每秒进行十次过期扫描,过期扫描不会遍历过期字典中所有的 key,而是采用了一种简单的贪心策略。
1.从过期字典中随机 20 个 key;
2.删除这 20 个 key 中已经过期的 key;
3.如果过期的 key 比率超过 1/4,那就重复步骤 1;
同时,为了保证过期扫描不会出现循环过度,导致线程卡死现象,算法还增加了扫描时间的上限,默认不会超过 25ms。

从库的过期策略

从库不会进行过期扫描,从库对过期的处理是被动的。主库在 key 到期时,会在 AOF 文件里增加一条 del 指令,同步到所有的从库,从库通过执行这条 del 指令来删除过期的 key。
因为指令同步是异步进行的,所以主库过期的 key 的 del 指令没有及时同步到从库的话,会出现主从数据的不一致

Redis的 回收策略(淘汰策略)

  • noeviction:
    当 Redis 缓存达到了 maxmemory 配置的值后,再有写入请求到来时,redis 将不再提供写入服务,直接响应错误 【默认
  • volatile-lru:
    从已设置过期时间的数据集中挑选【最近最少使用的】数据淘汰
  • volatile-random:
    从已设置过期时间的数据集中【随机选择】数据淘汰
  • volatile-ttl:
    从已设置过期时间的数据集中挑选将【要过期的】数据淘汰
  • allkeys-lru:
    从数据集中挑选【最近最少使用】数据淘汰
  • allkeys-random:
    从数据集中【随机选择】数据淘汰
  • no-enviction(驱逐):
    禁止驱逐数据 【永不回收】的策略。

数据明明过期了,怎么还占用着内存?

这是由 redis 的过期策略来决定。

redis 过期策略是:定期删除+惰性删除
所谓定期删除,指的是 redis 默认是每隔 100ms 就随机抽取一些设置了过期时间的 key,检查其是否过期,如果过期就删除。
假设 redis 里放了 10w 个 key,都设置了过期时间,你每隔几百毫秒,就检查 10w 个 key,那 redis 基本上就死了,cpu 负载会很高的,消耗在你的检查过期 key 上了。注意,这里可不是每隔 100ms 就遍历所有的设置过期时间的 key,那样就是一场性能上的灾难。实际上 redis 是每隔 100ms 随机抽取一些 key 来检查和删除的。

但是问题是,定期删除可能会导致很多过期 key 到了时间并没有被删除掉,那咋整呢?所以就是惰性删除了。这就是说,在你获取某个 key 的时候,redis 会检查一下 ,这个 key 如果设置了过期时间那么是否过期了?如果过期了此时就会删除,不会给你返回任何东西。

但是实际上这还是有问题的,如果定期删除漏掉了很多过期 key,然后你也没及时去查,也就没走惰性删除,此时会怎么样?如果大量过期 key 堆积在内存里,导致 redis 内存块耗尽了,咋整?
答案是:走内存淘汰机制。

©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容