布隆过滤器解决缓存穿透问题
作者:互联网
背景:很多商城,商品详情的链接格式:https://item.jd.com/100005786822.html,不同的商品详情的链接不一样的地方在于商品编号,如,我有个商品1002002,那么商品详情的链接为https://item.jd.com/1002002.html;
当我们访问商品详情链接时,后台的逻辑:先从redis中查询该商品,如果不存在,再查数据库。我们分析一下,感觉逻辑没问题,但是,如果访问的商品不存在呢?如果我写个死循环去调用不存在的商品详情会怎么
样,如下代码:
如果后台没作特别处理,这样数据库会挂掉,进而系统也会挂掉?
怎么解决这个问题呢?那就要用到布隆过滤器了:
布隆过滤器由一个二进制的数组组成:我们假设总共商品只有3个,分别为A,B,C 布隆过滤器的数组长度是10,初始化时,每个索引对应的值都是0,因为二进制不是0就是1:
现在将所有商品初始化进布隆过滤器,如A,先经过一个算法,得出A在数组哪个索引的值为1,然后又经过另一个算法,得出A在数组哪个索引值为1,最后再经过一次不同的算法得到A在哪个索引的值为1;
假如经过三次计算,A在索引1,3,5的值都为1;此时的数组:
同理,如果B商品经过三次计算,在0,3,7的值为1,因为索引3的值已经是1了,所以索引3不用再变更:
假如C商品经过计算得到1,4,5的值为1
至此,布隆过滤器初始化完毕,此时发现索引2,8,9的值都是0,证明没有商品命中,现在如果被人恶意攻击,传了一个商品D,
经过三次计算,假如结果是0,2,7的结果是1,但布隆过滤器中索引2的值是0,这就说明了布隆过滤器没有这个商品,因此没有命中商品直接返回前端即可;
假如另一个商品E经过计算,索引0,1,3的值为1,通过布隆过滤器对比,发现,命中了,但此时,商品不一定存在,将会放行,先查redis,redis没有命中再查数据库;
上面就是布隆过滤器的原理了,通过分析,我们只要数组够大,计算次数过多,这样过滤不存在商品的概率就越大;
总结布隆过滤器的特点:没命中,肯定不存在,命中,不一定存在;
开发中使用:redisson框架实现了该功能,提供了一个初始化布隆过滤器数组大小的方法,还有一个add商品到布隆过滤器的方法,以及判断某个值在不在过滤器的方法;
提示:布隆过滤由于是二进制的数组,因此一个长度一亿的布隆过滤器也不会占用多大的内存,详细,一个int类型的数字都32位了
标签:缓存,索引,布隆,命中,商品,数组,过滤器 来源: https://www.cnblogs.com/yangxiaohui227/p/15163474.html