首页 > 其他分享 >布隆过滤器:原理介绍与实战

布隆过滤器:原理介绍与实战

时间:2023-12-23 15:33:42浏览次数:28  
标签:实战 下标 哈希 元素 布隆 数组 过滤器

布隆过滤器

用一句话来说,布隆过滤器是为了解决查询一个元素是否存在于某个集合之中

例如:50亿个用户ID,查询某ID是否在这50亿集合之中。

50亿*8字节大约为50GB,内存占用极大。

所以一般采用 位数组,以及位数组的延伸设计:布隆过滤器。

在学习布隆过滤器之前,我们需要有些基础性概念:

哈希函数

哈希函数,即散列函数。它可以任意长度的输入通过算法转换成一个定长的输出,这个输出就是散列值,或者叫哈希值

因为是无穷对应有限,则必有多个输入对应相同的输出,即散列冲突,或叫哈希冲突

哈希算法有以下特点:

  • 从输出无法推导出输入。
  • 散列冲突的概率要尽可能小。
  • 数据敏感,对输入的简单修改会导致输出的巨大差异。

位数组

位数组本质上是一个超长的bit数组,数组元素只能为0或1。

根据上文,如果50亿个用户ID是有序的,使用bit数组实际上很好判断。

将每个ID映射到数组下标之中,用1代表存在,0代表不存在,如果有一段数学意义上连续的ID,还可以用一位数组下标映射一段ID,内存占用将更小。

但如果用户ID不是自增的,如果50亿用户ID,按照ID为10位来计算,将有超过90亿种可能排列,使用位数组要占用超过100GB内存。

这几乎是无法接受的。

布隆过滤器

布隆过滤器(Bloom Filter)的核心组件是一个超长的位数组和若干个哈希函数

布隆过滤器的查询复杂度为O(k),k为哈希函数的个数并且支持并发修改或查询

设数组长度为m,哈希函数个数为k。

在初始状态下,数组每个元素都被设置为0。

当有元素加入过滤器时,通过k个哈希函数,计算k个数组下标,并将数组下标所在元素置为1。

当查询时,再次通过k个哈希函数,计算得k个数组下标,并检查数组下标是否全部为1。若是,则该元素存在于集合中,反之则不存在于集合中。

1.png

误判问题

通过上述插入与查询逻辑可以推导得:

布隆过滤器不会将集合里的元素误判为不在集合之中。

用具象的话来理解就是:宁可放过,绝不误伤

这很好理解,如果在集合内的元素,哈希计算后的下标所对应的元素都为1,不会出现误伤现象。

而如果反过来想想,如果这个元素不在集合之中,由于哈希冲突,在极端情况下,该元素所有哈希计算后的下标对应元素都为1,那么可能会造成不在集合之中的元素放行

所以造成了布隆过滤器的误判问题。

误判率计算

设数组长度为m,哈希函数个数为k,数组内已添加n个元素。

则可以推导:

  • 数组中某一特定的位在进行元素插入时的 Hash 操作中没有被置1的概率是:

    $$ 1-\frac{1}{m} $$

  • 在所有 k 次 Hash 操作后该位都没有被置 1 的概率是: $$ (1-\frac{1}{m})^{k} $$

  • 如果我们插入了 n 个元素,那么某一位仍然为 0 的概率是: $$ (1-\frac{1}{m})^{kn} ≈ e ^ \frac{-kn}{m} $$

  • 该位为 1 的概率是: $$ 1 - (1-\frac{1}{m})^{kn} ≈ 1 - e ^ \frac{-kn}{m} $$

  • 则经过 k 个哈希函数后仍然错误的概率为: $$ (1 - e ^ \frac{-kn}{m}) ^ {k} $$

求最优参数

根据布隆过滤器性质可知,k 必须为整数。

在一般情况下,m 与 n 不在开发者能调控的范围之内。

所以一般最优参数都指的是求 k 的最优参数,即:在 k 为何值时,过滤器的误判率最小

根据数学性质,对于给定的 mn,最小化误报概率的 k 值为: $$ k = \frac{m}{n}ln2\quad(ln2≈0.693) $$

布隆过滤器的删除问题

在布隆过滤器中,一般情况下是无法删除元素的,因为存在哈希冲突,所以可能会把其他元素对应的下标置为0,导致未被删除的元素被误认为不存在集合之中

为了解决这个问题,可以采用 计数删除 方案。

简单来说,为每个下标计数,如果下标被置为 1 则为计数器 +1,反之则减1。

这样会保留下来其他元素的映射信息。

计数回绕

同时,这种方法会存在计数回绕问题。

计数器类型为了节省内存,一般用unsigned修饰,它只能表示非负整数,因此其取值范围是从0到最大值。例如,如果使用8位无符号整数,其取值范围是0到255。

当计数器的值达到最大值时,再进行+1操作会导致计数器值溢出,即超出了它能表示的最大值,导致计数器的值变为0。这个过程就是计数回绕,这导致当哈希冲突次数过多,超过计数器类型能表示的范围时,计数器反而会变成0,影响布隆过滤器的判断。

同理,当计数器为0且 -1 时,也会导致计数器值溢出。

标签:实战,下标,哈希,元素,布隆,数组,过滤器
From: https://blog.51cto.com/ErickRen/8945264

相关文章

  • 实战经验分享:开发同城外卖跑腿小程序
    下文,小编将与大家一同探究同城外卖跑腿小程序的开发实战,包括但不限于技术选型、开发流程、用户体验等多个方面。 1.技术选型在同城外卖跑腿小程序的开发中,技术选型是至关重要的一环。对于前端,选择了使用Vue.js框架,其灵活性和生态系统的支持使得开发过程更加高效。 后端方面,采用了......
  • Spring Boot之@Autowired注解使用区别,实战演示?
    ......
  • 26.基于 page object 模式的测试框架优化实战
    目录异常处理(弹窗黑名单)日志记录报告生成测试数据的数据驱动异常弹框处理定义黑名单列表处理弹框#声明一个黑名单defblack_wrapper(fun):defrun(*args,**kwargs):basepage=args[0]try:returnfun(*args,**kwargs)......
  • LangChain学习三:链-实战
    文章目录上一节内容:LangChain学习二:提示-实战(下半部分)学习目标:明白链是什么?有哪些?怎么用?学习内容一:介绍学习内容二:有那些学习内容三:实战3.1LLMChain3.1.1声明:接入大模型、声明PromptTemplate、LLMChain3.1.2送入大模型3.1.3.多个参数3.2顺序链上一节内容:LangChain学习二:提示-......
  • 【PySide6】信号(signal)和槽函数(slot),以及事件过滤器
    https://blog.csdn.net/qq_25262697/article/details/129374905说明在PYQT中,父控件可以通过两种方式响应子控件的事件:通过信号(signal)和槽函数(slot)机制连接子控件和父控件父控件可以通过设置eventFilter()方法来监听响应子控件的事件一、信号(signal)和槽函数(slot)示例在PYQ......
  • java接口自动化测试实战003----fastjson处理传入参数为JSON格式数据
    一、fastjson概述1、概述   fastjson是阿里爸爸开发的一款专门用于Java开发的包,可以方便的实现json对象与JavaBean对象的转换,实现JavaBean对象与json字符串的转换,实现json对象与json字符串的转换。2、常用API   fastjsonAPI入口类是com.alibaba.fastjson.JSON,常......
  • java接口自动化测试实战002----测试数据封装及ExcelUtil优化
    一、利用testNG测试框架进行封装1、封装实现新建测试类,类中新增多个方法,每个方法存储一条测试数据并调用HttpUtl类中的doGet或doPost方法。缺点:代码复杂、繁琐,且不适用测试数据量大的情况。2、封装步骤(1)maven的pom.xml文件中添加testNG测试框架的依赖,如下所示:<!--https://......
  • java接口自动化测试实战004----分表存储接口信息和用例信息之CaseUtil和RestUtil
    一、分表存储用例信息和接口信息1、实现思想  将用例相关信息存储在用例表单中,将接口信息存储在接口信息表单中,创建对应的类存储表单中的信息。2、实现步骤(1)修改表格文件,分表存储用例信息和接口信息,如下图所示:     (2)修改ExcelUtil中的读取函数datas,让表单名称......
  • Python+Selenium框架实战系列003----测试数据分离与ddt技术&断言
    一、测试数据分离1、新建testData文件夹,新建login_data.py文件,如下所示:   2、在login_datas.py文件中存放测试用例数据,如下所示:#正常场景success_data={"mobile":"17839196010","pwd":"duhui94619"}#异常用例--手机号异常phone_data=[{"mobile":&......
  • [字符编码] 实战篇:QT中文乱码的解决办法
    作者:丶布布1.编码科普常见的两种编码是:UTF-8和GBK:UTF-8:编码包含全世界所有国家需要用的字符,它比较灵活,长度在1-6个字节,UTF-8编码格式很强大,支持所有国家的语言,如果你的网站涉及到多个国家的语言,那么建议你选择UTF-8编码。正是因为它的强大,才会导致它占用的空间大小要比GBK大,对于......