redis 过期策略

Redis 使用过期字典和惰性策略管理过期 key,避免因大量 key 同时过期导致性能问题。默认每秒扫描十次,随机选取20个 key,若过期比例超1/4则继续,但总耗时不超过25ms。业务开发人员应注意避免大批量 key 同时过期,设置随机过期时间。

Redis 所有的数据结构都可以设置过期时间,时间一到,就会自动删除。你可以想象 Redis 内部有一个死神,时刻盯着所有设置了过期时间的 key,寿命一到就会立即收割。

你还可以进一步站在死神的角度思考,会不会因为同一时间太多的 key 过期,以至于忙不过来。同时因为 Redis 是单线程的,收割的时间也会占用线程的处理时间,如果收割的太过于繁忙,会不会导致线上读写指令出现卡顿。

这些问题 Antirez 早就想到了,所有在过期这件事上,Redis 非常小心。

过期的 key 集合

redis 会将每个设置了过期时间的 key 放入到一个独立的字典中,以后会定时遍历这个字典来删除到期的 key。除了定时遍历之外,它还会使用惰性策略来删除过期的 key,所谓惰性策略就是在客户端访问这个 key 的时候,redis 对 key 的过期时间进行检查,如果过期了就立即删除。定时删除是集中处理,惰性删除是零散处理。

定时扫描策略

Redis 默认会每秒进行十次过期扫描,过期扫描不会遍历过期字典中所有的 key,而是采用了一种简单的贪心策略。

  • 从过期字典中随机 20 个 key;
    删除这 20 个 key 中已经过期的 key;
    如果过期的 key 比率超过 1/4,那就重复步骤 1;
    同时,为了保证过期扫描不会出现循环过度,导致线程卡死现象,算法还增加了扫描时间的上限,默认不会超过 25ms。

设想一个大型的 Redis 实例中所有的 key 在同一时间过期了,会出现怎样的结果?

毫无疑问,Redis 会持续扫描过期字典 (循环多次),直到过期字典中过期的 key 变得稀疏,

Redis 提供了丰富的键过期策略和机制,以支持灵活的数据生命周期管理。在 Redis 中,可以通过设置键的生存时间(TTL, Time To Live)来控制键的自动删除行为。一旦键的 TTL 过期,它将被自动从数据库中移除。 ### 键的过期设置 Redis 支持多种方式为键设置过期时间: - **EXPIRE**:以秒为单位设置键的生存时间。 - **PEXPIRE**:以毫秒为单位设置键的生存时间。 - **EXPIREAT**:指定一个绝对时间点(Unix 时间戳,以秒为单位),当到达该时间点时,键将失效。 - **PEXPIREAT**:与 `EXPIREAT` 类似,但以毫秒为单位指定绝对时间点。 例如: ```bash SET mykey "Hello" EXPIRE mykey 60 # 设置键 mykey 的生存时间为 60 秒 ``` ### 键的过期策略 Redis 实现了以下几种主要的过期策略来平衡性能和内存使用: 1. **惰性删除(Lazy Expiration)** Redis 不会主动检查并删除已过期的键,而是等到客户端尝试访问某个键时才检查其是否过期。如果键已经过期,则将其删除并返回空值给客户端。这种策略的优点是节省 CPU 资源,但可能导致过期键长时间驻留在内存中,直到被访问为止。 2. **定期删除(Active Expiration)** Redis 每隔一段时间(默认每 100 毫秒)会随机检查一部分设置了过期时间的键,并删除其中已经过期的键。这一过程是渐进式的,不会一次性扫描所有键,从而避免对性能造成显著影响。这种方式可以在一定程度上减少内存浪费,同时保持系统的响应速度。 3. **混合模式** Redis 实际采用的是惰性删除和定期删除相结合的方式。这样既保证了大部分情况下不会因为检查过期键而消耗过多资源,又能及时清理掉一些长期未被访问但仍过期的键。 ### 过期键的存储结构 为了高效地处理设置了过期时间的键,Redis 使用了一个专门的字典(称为 `expires` 字典)来保存这些键及其对应的过期时间。每个设置了过期时间的键都会在这个字典中有一个条目,键本身仍然存在于主字典中,但其过期时间则记录在 `expires` 字典中。 ### 查看过期时间 用户可以使用以下命令来查询键的过期时间: - **TTL**:返回键的剩余生存时间(以秒为单位)。如果键没有设置过期时间,则返回 `-1`;如果键不存在或已过期,则返回 `-2`。 - **PTTL**:与 `TTL` 类似,但返回值是以毫秒为单位的剩余生存时间。 例如: ```bash TTL mykey ``` ### 复杂度与性能考虑 对于大多数实际应用场景来说,Redis 的键过期机制是非常高效的。然而,在某些极端情况下,比如大量键在同一时间点过期,可能会导致短暂的性能波动。为了避免这种情况,建议合理分布键的过期时间,或者通过程序逻辑引入一定的随机性来分散过期时间。 此外,需要注意的是,当数据量较大且频繁设置过期时间时,定期删除操作可能无法完全覆盖所有过期键,因此系统内存占用可能会有所增加。在这种情况下,可以适当调整 Redis 的配置参数(如 `maxmemory` 和 `maxmemory-policy`)来优化内存使用。 ---
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

韩淼燃

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值