三种特殊数据类型

bitmap

官方说明

bitmap 事实上不是数据类型,而是一组 定义在 string 类型上、面向二进制位** **的操作。string 数据类型是二进制安全的,并且它最大可存储 512MB 的值,因此 bitmap 可以存储 2^32 个不同的二进制位

bitmap 最大的优势之一是存储信息时,它经常可以极大的节省空间。例如,一个用户的系统中,使用递增的 id 来表示不同的用户,这时候 bitmap 使用 512MB 内存就可以记录 40 亿用户的一个比特信息(例如,1是男生,0是女生,一个男生的id为19,那么这个 bitmap 的第 19 位就是 1)。

通常 bitmap 的使用例子是:

  • 各种实时分析
  • 存储于对象 id 相关联的、节省空间的、高性能的布尔信息

setbit

向 key 中设置一个 bit

127.0.0.1:6379> setbit mybit 0 1
(integer) 0

127.0.0.1:6379> setbit mybit 10 1
(integer) 0

127.0.0.1:6379> setbit mybit 15 0
(integer) 0
复制代码

第一个参数是 key 的名称,第二个是 bit 在第几位,第三个是 bit 的值(0或1)

getbit

获取 bitmap 中指定位置的 bit 值,没有设置过值的位默认为0

127.0.0.1:6379> setbit mybit 0 1
(integer) 0

127.0.0.1:6379> setbit mybit 10 1
(integer) 0

127.0.0.1:6379> setbit mybit 15 0
(integer) 0

127.0.0.1:6379> getbit mybit 0
(integer) 1

127.0.0.1:6379> getbit mybit 10
(integer) 1

127.0.0.1:6379> getbit mybit 15
(integer) 0

127.0.0.1:6379> getbit mybit 16     # 没有设置过值的位默认为0
(integer) 0
复制代码

bitcount

计算 bitmap 中存储的 1 的个数

127.0.0.1:6379> setbit mybit 0 1
(integer) 0

127.0.0.1:6379> setbit mybit 10 1
(integer) 0

127.0.0.1:6379> setbit mybit 15 0
(integer) 0

127.0.0.1:6379> bitcount mybit
(integer) 2
复制代码

bitpos

找出 bitmap 中指定范围内第一个 0 或 1 的位置

127.0.0.1:6379> setbit mybit 3 0
(integer) 0

127.0.0.1:6379> setbit mybit 5 1
(integer) 0

127.0.0.1:6379> setbit mybit 7 1
(integer) 0

127.0.0.1:6379> bitpos mybit 1 0 -1       # 最后两个参数设置检索范围, 0 -1 表示所有的数
(integer) 5

127.0.0.1:6379> bitpos mybit 0 0 -1
(integer) 0
复制代码

bitop

对多个 bitmap 进行 and(与)、or(或)、xor(异或)操作,还有针对一个 bitmap 的 not(非) 这里只对 or 操作进行演示

127.0.0.1:6379> setbit mybit1 0 1
(integer) 0

127.0.0.1:6379> setbit mybit1 1 0
(integer) 0

127.0.0.1:6379> setbit mybit2 0 0
(integer) 0

127.0.0.1:6379> setbit mybit2 1 1
(integer) 0

127.0.0.1:6379> bitop or mybit3 mybit1 mybit2
(integer) 1

127.0.0.1:6379> getbit mybit3 0
(integer) 1

127.0.0.1:6379> getbit mybit3 1
(integer) 1

复制代码

HyperLogLogs

什么是基数

基数是一个集合中不重复的元素,例如 A{1,1,2,3,4,4,5} 这个集合的基数是 5

官方说明

超日志(HyperLogLog)是一种概率数据结构,用于统计唯一的事物(从技术上讲,这是指估计集合的基数)。通常,计算唯一项目需要使用与要计数的项目数成比例的内存量,因为您需要记住您在过去看到的元素,以避免多次计数。但是,有一组算法会以内存换取精度:您最终会得到带有标准误差的估计量,在Redis实现的情况下,该误差小于1%。该算法的神奇之处在于,您不再需要使用与所计数项目数成正比的内存量,而是可以使用固定的内存空间!在最坏的情况下为12k字节,如果您的HyperLogLog(从现在开始将它们称为HLL)的元素很少,则使用内存更少。

Redis中的HLL尽管在技术上是不同的数据结构,但被编码为Redis String,因此您可以调用GET来序列化HLL,然后调用SET来将其反序列化回服务器。

然而您并没有真正将项添加到HLL中,因为它的数据结构只存储不含实际元素的状态

使用场景 一个人访问一个网站多次,但是还是算作一个人

传统方式:使用 set 来存储访问的人的 id,但是这样 set 集合中会存储大量的用户 id,我们的目的是计数,不是存储 id。

现在解决方案:使用 hyperloglog 数据类型,因为它不是真正的添加元素到 HLL 中,占用内存很小

pfadd

把一个或多个值添加到数据类型为 hyperLogLogs 的 key 中

127.0.0.1:6379> pfadd hyper a b c d
(integer) 1
复制代码

pfcount

计算一个或多个key中存储的元素的个数

127.0.0.1:6379> pfadd hyper a b c d
(integer) 1

127.0.0.1:6379> pfadd info d g h
(integer) 1

127.0.0.1:6379> pfcount hyper info
(integer) 6

127.0.0.1:6379> pfcount hyper
(integer) 4
复制代码

pfmerge

合并多个 key 中的数据到一个 key

127.0.0.1:6379> pfadd hyper a b c d
(integer) 1

127.0.0.1:6379> pfadd info d g h
(integer) 1

127.0.0.1:6379> pfmerge test hyper info
OK

127.0.0.1:6379> pfcount test
(integer) 6
复制代码

geospatial

官方说明

这个数据类型可以存储地球上地理位置的经纬度信息,能够通过经纬度信息计算出两地之间的距离,能够通过坐标和半径的方式找出范围内的其他地理位置

如果你的程序需要使用 附近的人 的功能,使用 geospatial 数据类型就能做到。

geoadd

添加一个或多个带有经纬度的地理位置

# 格式:geoadd key 经度 维度 地点名称  [经度 维度 地点名称 ...]

127.0.0.1:6379> geoadd geo 120.21201 30.2084 hangzhou 121.48941 31.40527 shanghai  
(integer) 2                                                                                             
复制代码

geodist

返回两地之间的距离

127.0.0.1:6379> geoadd geo 120.21201 30.2084 hangzhou 121.48941 31.40527 shanghai  
(integer) 2                                               

127.0.0.1:6379> geodist geo hangzhou shanghai km   # 最后一个参数指定单位
"180.5896"
复制代码

[图片上传失败...(image-5ae9a6-1602473117944)]

geohash

获取一个或多个地点的 geohash 值,这个 geohash 其实就是地点的经纬度信息经过编码形成的,每个字符串代表唯一的坐标

127.0.0.1:6379> geoadd geo 120.21201 30.2084 hangzhou 121.48941 31.40527 shanghai  
(integer) 2   

127.0.0.1:6379> geohash geo hangzhou shanghai
1) "wtm7z7r8wv0"
2) "wtw6st1uuq0"
复制代码

geopos

返回一个或多个地理位置的经纬度坐标

127.0.0.1:6379> geoadd geo 120.21201 30.2084 hangzhou 121.48941 31.40527 shanghai  
(integer) 2   

127.0.0.1:6379> geopos geo hangzhou shanghai
1) 1) "120.21200805902481079"
   2) "30.20839995425554747"
2) 1) "121.48941010236740112"
   2) "31.40526993848380499"
复制代码

georadius

给定一个坐标作为圆心,给定一个距离作为半径,扫描这个圆范围内的地点(前提是redis中存在)

127.0.0.1:6379> geoadd geo 120.21201 30.2084 hangzhou 121.48941 31.40527 shanghai  
(integer) 2  

127.0.0.1:6379> geoadd geo 113.27324 23.15792 guangzhou 91.13775 29.65262 xizang  
(integer) 2 

# 格式:georadius key 经度 维度 半径 单位 [可选项,见官网]
127.0.0.1:6379> georadius geo 120.21201 30.2084 200 km  # 以杭州为中心200km为半径扫描
1) "hangzhou"
2) "shanghai"

127.0.0.1:6379> georadius geo 120.21201 30.2084 5000 km  # 杭州为中心,5000km为半径扫描
1) "xizang"
2) "guangzhou"
3) "hangzhou"
4) "shanghai"
复制代码

georadiusbymember

这个命令和 georadius 命令一样, 都可以找出位于指定范围内的元素, 但是 georadiusbymember 的中心点是由给定的位置元素决定的, 而不是像 georadius 那样, 需要输入的经度和纬度来决定中心点。

127.0.0.1:6379> geoadd geo 120.21201 30.2084 hangzhou 121.48941 31.40527 shanghai  
(integer) 2  

127.0.0.1:6379> geoadd geo 113.27324 23.15792 guangzhou 91.13775 29.65262 xizang  
(integer) 2 

127.0.0.1:6379> georadiusbymember geo hangzhou 200 km
1) "hangzhou"
2) "shanghai"
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 204,293评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,604评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,958评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,729评论 1 277
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,719评论 5 366
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,630评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,000评论 3 397
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,665评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,909评论 1 299
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,646评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,726评论 1 330
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,400评论 4 321
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,986评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,959评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,197评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 44,996评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,481评论 2 342