Redis:key过期策略、缓存穿透、缓存击穿、缓存雪崩

key的过期策略

Redis 使用 惰性删除 + 定期删除
redis 数据库由dictexpires两个字典组成

  • dict 负责存储所有的键值对
  • expires 负责存储键的过期时间

Redis中可以对键设置过期时间,key过期后,Redis是如何处理的?

  • redis提供了三种方式:立即删除、惰性删除、定时删除

1.立即删除

给key设置过期时间时,创建回调函数,当key有效期结束后立即执行回调函数,删除键释放内存。

缺点:删除操作会占用cpu时间,影响redis性能

2.惰性删除

一个key过期后,不会立刻删除,等到下一次使用这个key时,检测到过期,此时才删除它。

缺点:若键过期了,一直没有被再次使用,会浪费内存(dict和expires字典中都要保存key-value的信息)。

3.定时删除

每隔一段时间,对存储键过期时间的expires字典进行检查,随机选取一些key检查过期就删除。

缓存的处理流程

  1. 前端发送请求,请求先到达redis,在redis缓存中查询是否有该数据,有就返回,没有就去数据库中查询。
  2. 在数据库中查询,数据库中有数据,同步到redis缓存,同时返回给前端。没有数据返回空。

缓存穿透

穿透的原因

请求的数据在redis缓存中不存在,数据库中也没有该数据,请求每次直接穿透打在数据库中。

例:查询数据库中id为-1的数据,每次都会穿透redis访问数据库,大量恶意请求可能导致数据库挂掉。
在这里插入图片描述

总结:缓存和数据库中都没有该数据

如何解决穿透?

  1. 将空对象返回给前端,并将空对象同步到缓存中。(给空对象设置较短的过期时间)
  2. 检验参数的合法性,不合法直接return
  3. 使用布隆过滤器

缓存击穿

击穿的原因

大量请求访问热点key,若key到期失效了,此时大量的请求直接到达数据库,可能导致数据库挂掉。
在这里插入图片描述

如何解决击穿?

  1. 设置key永久有效
  2. 这种情况是多个线程同时到达数据库查询该数据。可以给第一个请求的线程上锁。
    1. 在第一个请求的线程上加互斥锁,其他线程等着
    2. 持有锁的第一个线程查询到了数据,将数据同步到redis缓存
    3. 后面的线程在redis中查询到了数据,就不会到达数据库发生击穿了

缓存雪崩

雪崩的原因

在高并发下,大量redis缓存在同一时间失效到期或redis故障,所有的请求都会到达数据库,可能导致数据库挂掉。
在这里插入图片描述

如何解决雪崩?

  1. 不设置过期时间,默认永久有效,就不会发生雪崩了,但是浪费内存。
  2. 既然是同一时间失效导致的雪崩,我们随机初始key的过期时间,避免大量Key同时过期。
  3. 如果redis集群,将热点key平均分布到不同的redis结点上去,避免集体失效。
  4. 定时任务,在缓存失效前将缓存重新跑进去。

总结:

缓存穿透是缓存和数据库中都没有数据,一直查询数据库
缓存击穿是热点key突然失效,大量请求到达数据库
缓存雪崩是大面积(大量)key同时失效,大量请求到达数据库

如何避免redis宕机,请求全到达数据库的情况?

  • 未宕机 :redis的高可用性(主从复制+哨兵机制),避免redis挂掉
  • 已宕机 :redis宕机,设置本地缓存(ehcahe + 限流),避免请求全走数据库
  • 宕机后 :redis持久化,重启后将数据从磁盘中加载到内存中来
  • 0
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值