redis003--节衣缩食(位图)

在我们平时开发过程中,会有一些 bool 型数据需要存取,比如用户一年的签到记录,签了是 1,没签是 0,要记录 365 天。如果使用普通的 key/value,每个用户要记录 365
个,当用户上亿的时候,需要的存储空间是惊人的。

为了解决这个问题,Redis 提供了位图数据结构,这样每天的签到记录只占据一个位,365 天就是 365 个位,46 个字节 (一个稍长一点的字符串) 就可以完全容纳下,这就大大节约了存储空间。

位图不是特殊的数据结构,它的内容其实就是普通的字符串,也就是 byte 数组。我们
可以使用普通的 get/set 直接获取和设置整个位图的内容,也可以使用位图操作 getbit/setbit
等将 byte 数组看成「位数组」来处理。

统计和查找

Redis 提供了位图统计指令 bitcount 和位图查找指令 bitpos,bitcount 用来统计指定位置范围内 1 的个数,bitpos 用来查找指定范围内出现的第一个 0 或 1。

比如我们可以通过 bitcount 统计用户一共签到了多少天,通过 bitpos 指令查找用户从哪一天开始第一次签到。如果指定了范围参数[start, end],就可以统计在某个时间范围内用户签到了多少天,用户自某天以后的哪天开始签到。

遗憾的是, start 和 end 参数是字节索引,也就是说指定的位范围必须是 8 的倍数,而不能任意指定。这很奇怪,我表示不是很能理解 Antirez 为什么要这样设计。因为这个设计,我们无法直接计算某个月内用户签到了多少天,而必须要将这个月所覆盖的字节内容全部取出来 (getrange 可以取出字符串的子串) 然后在内存里进行统计,这个非常繁琐。

©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • ORA-00001: 违反唯一约束条件 (.) 错误说明:当在唯一索引所对应的列上键入重复值时,会触发此异常。 O...
    我想起个好名字阅读 10,794评论 0 9
  • Redis key 值是二进制安全的,这意味着可以用任何二进制序列作为key值,从形如”foo”的简单字符串到一个...
    壹点零阅读 5,323评论 0 2
  • 0. 引言 基于Redis丰富的数据结构,除了充当缓存层来提升查询效率以外,还能应用在很多常见的场景,比如:分布式...
    BeckJiang阅读 6,109评论 0 13
  • 位图(Bitmap) 什么是位图?一串连续的二进制数字,每一位所在的位置为偏移量(offset), 在位图上可执行...
    芒果菠萝蛋炒饭阅读 3,051评论 0 0
  • 1. 事件:老板一封邮件出来,呼吁大家头脑风暴,想出2016节约成本的机会……多日过去,整个部门无一人回应。老板最...
    笔立悟_Believe阅读 1,423评论 0 0