大家好,我是北军。正如标题所说,让我们来看看一个经常听到但今天可能不会用到的技术。GuavaBloomFilter布隆过滤器是一个长二进制向量和一系列随机映射函数。布隆过滤器可用于检索元素是否在集合中。它的优点是空间效率和查询时间都比一般算法好很多,缺点是存在一定的误识别率和删除难度。基本概念当需要判断某个元素是否在某个数据集中时,一般会怎么做?将数据集封装成一个集合比较简单,比如List、Set等,通过集合提供的API来判断元素是否存在于集合中。同时,现有的JDK可以快速达到目的,但是试想一下,如果上面说的采集数据量非常大,不仅会消耗大量的存储空间,还会增加获取元素的时间复杂度集合。那么判断元素是否存在的情况有没有更好的实现方式呢?那就是布隆过滤器。通过一系列的Hash函数,将元素映射到一个位数组(BitArray)中的多个点,判断一个元素是否存在,就是判断所有的点是否都为1。但是位数组中并不全为1必然保证该元素存在,也有可能其他元素在Hash后落在这一点上,就是Bloomfilter的误判。因此,通过布隆过滤器,我们可以判断元素可能在集合中,元素一定不在集合中。应用场景网络爬虫忽略已经确定的URL路径。通过设置过滤器垃圾邮件集合中重复元素的识别,可以有效地判断该元素不在集合中并加以阻止。数据缓存时缓存穿透问题的优缺点优缺点与其他数据结构相比,布隆过滤器在空间和时间上具有巨大的优势。布隆过滤器存储空间和插入/查询时间都是常数。哈希函数之间没有任何关系,因此可以用硬件并行实现。布隆过滤器不需要存储元素本身,这在保密性要求非常严格的场合具有优势。布隆过滤器可以表示集成,其他数据结构都做不到。缺点元素存在的误判一般不支持删除元素(位数组)。实现原理的核心其实就是如何存储元素?如何检查元素是否存在?核心方法只有两个,一个是“保存”,一个是检查,涉及到算法相关的知识。有兴趣的可以深入研究其实现原理和思路。put将元素放入过滤器,但不放入存储空间//位数组,可以通过redis实现分布式布隆过滤器longhash64=Hashing.murmur3_128().hashObject(object,funnel).asLong();//通过funnel将object转化为基本类型并计算64位hashinthash1=(int)hash64;//取低32位inthash2=(int)(hash64>>>32);//取高32位booleanbitsChanged=false;//for(inti=1;i<=numHashFunctions;++i){intcombinedHash=hash1+i*hash2;如果(combinedHash<0){combinedHash=~combinedHash;}bitsChanged|=bits.set((long)combinedHash%bitSize);}返回bitsChanged;}mightContain和put类似,计算过程一样,不同的是值判断public
