Redis深入解析:HyperLogLog、Bitmap和Geospatial的奇妙应用

devtools/2024/12/22 20:55:13/

本文深入探讨了Redis数据库中的三种特殊数据类型:HyperLogLogBitmapGeospatial

  • HyperLogLog用于高效估算集合基数,牺牲小部分准确度以节省空间
  • Bitmap提供位操作,适用于二元数据的高效记录与查询
  • Geospatial处理地理位置数据,支持计算距离和范围搜索

HyperLogLog_7">HyperLogLog(基数统计)

HyperLogLog 是一种概率数据结构,用于估算集合的基数,即不重复元素的数量。

HyperLogLog通过牺牲一定的准确度来换取空间的高效利用。Redis 中的HyperLogLog实现使用最大12KB的内存,并提供小于1%的标准误差率

命令

PFADD key element [element ...]

HyperLogLog数据结构添加一个或多个元素。每个元素会被添加到指定的HyperLogLog键中,用于更新基数估计。

PFCOUNT key [key ...]

返回给定一个或多个HyperLogLog键的基数估计值。这些键中的每个元素都会被计入,以提供一个总的近似基数计数。

PFMERGE destkey sourcekey [sourcekey ...]

将多个HyperLogLog数据结构合并到一个单一的HyperLogLog数据结构中,结果存储在destkey中。合并后的HyperLogLog提供了所有源HyperLogLog键中观察到的唯一元素的近似基数计数。

经典使用场景

  1. 网站UV统计HyperLogLog非常适合用来统计网站的独立访客数量(UV)。由于其低内存消耗,它可以在不牺牲太多准确度的情况下,高效地处理大规模的用户访问数据
  2. 大型集合的基数估计:当需要对一个非常大的数据集进行基数估计时,使用HyperLogLog可以大大节省内存开销,同时保证误差在一个可接受的范围内
  3. 缓存穿透保护:对于缓存穿透问题,可以使用HyperLogLog记录已经查询过的数据标识符,快速判断请求是否重复,从而避免对数据库的无效查询

场景设计

应用场景:视频/直播间正在观看人数,允许误差和分钟级延迟
设计方案:结合HyperLogLog和过期时间的特性,能够有效地统计每分钟的观看人数

  • 缓存key为视频/直播间ID + 分钟级的时间戳
  • 当前在观看的每个客户端每分钟请求一次服务器(或心跳),统计至HyperLogLog
  • 查询观看人数时,查询上一分钟的HyperLogLog即可

由于HyperLogLog是一种基数估计算法,所以得到的观看人数是近似值,并不是精确的计数。在实际应用中,需要根据精确度要求和业务场景对结果进行合理的评估和调整

具体方案:

  1. 缓存键设计:将视频或直播间ID与分钟级时间戳结合作为缓存的键,可以确保每分钟的观看人数数据得到有效区分和存储。这样的设计可以方便地追踪特定视频或直播间在不同时间段内的观看人数。
  2. HyperLogLog数据结构:使用HyperLogLog作为观看人数的计数器是合适的选择。HyperLogLog可以在占用很小内存空间的情况下,对大量的唯一元素进行计数估计。由于每个客户端每分钟请求一次服务器并将用户或客户端ID添加到HyperLogLog中,可以粗略地估计每分钟的观看人数。
  3. 过期时间设置:将缓存数据的过期时间设置为几分钟,可以避免长期存储不再有效的数据,同时保持数据的实时性。过期时间的设置可以根据具体需求和业务场景来确定,确保及时清理不再需要的过期数据。
  4. 查询观看人数:使用PFCount命令可以获取每分钟的观看人数的近似值。通过对不同时间戳的HyperLogLog进行PFCount操作,可以得到每分钟的观看人数统计。

bitmap(位存储)

在Redis中,Bitmap是基于String类型实现的,可以高效地进行位操作,如设置位、获取位值、计算位的总数等

Bitmap(位图)是一种将每个元素映射到一个位上的数据结构,每个位只能表示0或1

命令

SETBIT key offset value:

设置或清除Redis字符串中的位。value可以是0或1,用于表示位的关闭或打开状态。

GETBIT key offset:

获取给定字符串键的位值。返回的是一个整数,表示指定偏移量上的位是0还是1。

BITCOUNT key [start end]:
```bash计算并返回字符串中位值为1的位的数量。可以通过指定start和end来限制计算的位范围。```bash
BITOP operation destkey key [key ...]:

对一个或多个BitMap进行位运算。operation可以是AND、OR、XOR或NOT,结果存储在destkey中

经典使用场景

  1. 签到打卡统计:可以使用Bitmap来记录用户每天的签到情况。每个用户对应一个Bitmap,每天对应一个位,签到则标记为1,未签到为0。这样可以高效地统计每月签到天数、连续签到情况等
  2. 活跃用户统计:通过记录用户每日的活跃状态,可以使用Bitmap来统计活跃用户数。每个用户对应一个位,活跃则标记为1,不活跃为0。这样可以快速统计出在一定时间范围内的活跃用户数量
  3. 实时数据分析:在需要实时分析大量二元数据的场景中,如股票市场中的买卖信号,可以使用Bitmap进行高效的数据记录和查询

geospatial (地理位置)

Geospatial(地理空间)是Redis用于处理地理位置相关数据的数据类型。它可以存储地理位置信息,并通过经纬度计算两个位置之间的距离,或者查询指定范围内的位置信息

命令

GEOADD key [NX|XX] [CH] longitude latitude member [longitude latitude member ...]:

向键key中添加一个或多个地理位置成员。NX和XX是可选标志,用于控制数据的添加行为,CH标志用于返回变化的计数。

GEOPOS key member [member ...]:

返回一个或多个成员的地理坐标。

GEODIST key member1 member2 [m|km|ft|mi]:

计算两个成员之间的距离,并返回结果。可以指定返回的距离单位。

GEOHASH key member [member ...]:

返回一个或多个成员的Geohash值。Geohash是一种对地理坐标进行编码的字符串,可以用来估计位置之间的距离。

GEOSEARCH key [FROMMEMBER member] [FROMLONLAT longitude latitude] [BYRADIUS radius m|km|ft|mi] [COUNT count [ANY]] [ASC|DESC]:

在指定范围内搜索成员,并按照与指定点之间的距离排序后返回。可以是圆形或矩形范围

经典使用场景

  1. 附近的人Geospatial可以用来实现“附近的人”这类功能。通过记录用户的地理位置信息,可以查询某个地点周围的用户,或者推荐附近的服务和设施5。
  2. 路线规划:利用Geospatial可以计算两个地点之间的距离,这对于路线规划和导航类应用非常有用。例如,可以计算出从A点到B点的直线距离,或者规划出一条避开拥堵区域的路线
  3. 地理围栏Geospatial可以用来创建地理围栏,监控进入或离开特定区域的对象,如车辆监控、人员定位等。
  4. 天气应用:在天气应用中,可以使用Geospatial来定位用户并提供相关的天气预报信息,如附近的雷暴警告或极端天气事件。
  5. 物流配送:物流行业可以利用Geospatial来优化配送路线,通过计算配送点之间的距离和位置信息,安排最高效的配送顺序和路径

参考资料:

  1. Redis入门 - 数据类型:3种特殊类型详解
  2. Redis:HyperLogLog使用与应用场景

http://www.ppmy.cn/devtools/2056.html

相关文章

EasyUI Jquery 学习笔记 ——DataGrid(数据网格)与 Tree(树)详细版

1. DataGrid(数据网格)与 Tree(树) 1.1 Datagrid 数据网格 扩展自 $.fn.panel.defaults。通过 $.fn.datagrid.defaults 重写默认的 defaults。 数据网格(datagrid)以表格格式显示数据,并为选择、排序、分组和编辑数据提供了丰富的支持。数据网格(datagrid)的设计目…

LinuxShell编程中source和export命令

目录 1.source命令1.1.POSIX模式1.1.1.验证POSIX模式执行情况 1.2.source命令表示形式的历史由来1.3.source命令解读1.3.1.在当前的shell环境中1.3.2.source命令的常用用途1.3.3.从文件名中读取并执行命令 2.export命令2.1.显示当前终端已经导出的函数和环境变量2.2.验证变量和…

多模态之ALBEF—先对齐后融合,利用动量蒸馏学习视觉语言模型表征,学习细节理解与论文详细阅读:Align before Fuse

Align before Fuse: Vision and Language Representation Learning with Momentum Distillation (ALBEF)在融合之前对齐:利用动量蒸馏进行视觉与语言表示学习 Paper: arxiv.org/pdf/2107.07651.pdf Github: https://github.com/salesforce/…

Java 的数据类型

文章目录 整型Java 和 C、C 在数据类型上的区别数据类型的后缀 浮点型十六进制表示浮点数值 字符型转义序列布尔型 Java 是一种强类型语言。 这意味着必须为每一个变量声明一种类型。 Java 中的基本数据类型分为8种 4种为:整型。 2种为:浮点类型。 1种为…

纯css实现switch开关

代码比较简单&#xff0c;有需要直接在下边粘贴使用吧~ html: <div class"switch-box"><input id"switch" type"checkbox"><label></label></div> css&#xff1a; .switch-box {position: relative;height: 25px…

Github 2024-04-16Python开源项目日报 Top10

根据Github Trendings的统计,今日(2024-04-16统计)共有10个项目上榜。根据开发语言中项目的数量,汇总情况如下: 开发语言项目数量Python项目10TypeScript项目1Vue项目1系统设计指南 创建周期:2507 天开发语言:Python协议类型:OtherStar数量:241693 个Fork数量:42010 次…

「前所未有!」服务网格与 Envoy Gateway,客户端可用性和弹性双提升,完美演绎 IT 新时代!

目录 如何从客户端角度思考服务的可用性和弹性 每个服务都有一个“网关” 以三个九的价格获得五个九的高可用能力&#xff1a;一个真实的案例 服务网格中的客户端负载均衡&#xff1a;超越组件之和 重试 异常检测 断路器 超时 限流 低成本下的高感知可用性 下一步 参…

第十五届蓝桥杯大赛软件赛省赛(Java 大学B组)

蓝桥杯 2024年省赛真题 Java 大学B组 试题 A: 报数游戏试题 B: 类斐波那契循环数试题 C: 分布式队列 在找工作&#xff0c;随便写写&#xff0c;安定下来再把去年国赛题解补上 试题 A: 报数游戏 本题总分&#xff1a; 5 5 5 分 【问题描述】 小蓝和朋友们在玩一个报数游戏。由…