Redis 击穿、穿透、雪崩的解决方案
击穿和穿透
场景: 指的是单个key在缓存中查不到,去数据库查询(透过redis去查db叫击穿) 区别: 击穿:数据在数据库中真实存在,缓存丢失,大量请求击穿数据库 穿透:数据在缓存中没有,数据库中也没有,就好像透过数据找数据一样 where id = 'xxx' (xxx在redis中不存在 -> 查DB)
while(true) { where id = UUID; }
雪崩
查询key并且出现"高并发",缓存中失效或者查不到,然后都去db查询,导致db压力飙升,从而崩溃。
解放方案
1.当查询数据不存在的时候,给设置一个空值的key进去并设置一个过期时间(最多5分钟)。"比较粗暴"
2.过滤器: 布隆过滤器:(Bloom Filter),google 的 Gauva 包中有布隆过滤的实现。 核心实现是一个超大的位数组和几个哈希函数。用到哈希就一定会存在哈希碰撞的问题(涉及到哈希算法的问题)。 可以理解为一个不怎么精确的set结构,使用 contains 方法判断某个对象是否存在。 只要参数设置的合理,它的精确度可以控制的相对足够精确,只会有小小的误判概率。 当布隆过滤器说某个值存在时,这个值可能不存在;当它说不存在时,那就肯定不存在。 缺点: 1.会存在一定的误判率 2.新增加的数据无法进行布隆过滤 3.数据的key不会频繁的更改 布谷鸟过滤器? 3.加锁排队: 加锁排队只是为了减轻数据库的压力,并没有提高系统吞吐量。 会导致用户等待超时,这是个治标不治本的方法! 注意:加锁排队的解决方式分布式环境的并发问题,有可能还要解决分布式锁的问题;线程还会被阻塞,用户体验很差!在高并发的环境下很少用
扩展 - 哈希碰撞?(不是很明白)