Redis专栏-基本数据类型介绍
Comment前言
Redis不仅仅是简单的键值对存储服务,它是一个支持 多种不同类型数据结构 数据的服务器。
它目前支持的数据类型:
- Binary-safe String: 二进制安全字符串
- List: 列表
- Set: 集合
- Sorted Set: 有序集合
- Hash: 哈希
- Bit Array:位数组,String的扩展
- HyperLogLogs:概率数据结构
- Stream:流
数据类型
Binary-safe String(二进制安全字符串)
String是Redis最基本、最简单的数据类型,它允许的最大密钥大小为512MB
,同时,值也不能大于512MB
,不过建议不要设置太长的key或value,否则它会给你带来巨大的内存开销。
同时,它是二进制安全的,所以它可以存储包括字符串在内的任何数据。
什么是二进制安全?
1 | 二进制安全功能(函数)是指在一个二进制文件上所执行的不更改文件内容的功能或者操作, |
注:SET
和GET
命令是我们设置和检索字符串值的方式
奇异的incr
:
1 | 看到这里,大家可能会疑惑了,我们在使用 incr/get 命令的时候,明明就是整型的数字啊! |
List(列表)
List是字符串元素的有序
集合,通过链表
实现,按照插入的顺序排序,元素可重复
。
链表(Linked list)是一种线性表,是很常见的基础数据结构,在每一个节点里存到下一个节点的指针,由于不必按顺序存储。
所以链表在插入的时候可以达到O(1)的复杂度,无论你在 1万 还是 1千万 的列表中,在其 左侧 或 右侧 添加元素的速度都是 非常快的、相同的。
但是访问速度不是那么快了,查找一个节点或者访问特定编号的节点则需要O(n)的时间,特别是LRANGE命令,查询时间复杂度:O(S+N), S 为偏移量 start , N 为指定区间内元素的数量,时间复杂度与所访问元素的索引量成正比。
常用的相关命令:
命令 | 解释 |
---|---|
LPUSH/RPUSH | 将一个新元素到列表的左侧(头部)/右侧(尾部) |
LRANGE | 从列表中提取指定范围的元素 |
LPOP/RPOP | 返回并移除列表左侧(头部)/右侧(尾部)的元素 |
LTRIM | 修剪指定范围的列表,让列表只保留指定范围的元素 |
LLEN | 获取列表的元素数量 |
适合的使用的场景:
- 作为消息队列
- 浏览足迹
Set(集合)
Set是字符串元素的无序
集合,通过哈希表
实现,元素不可重复
。
它的 添加、删除、查找 的复杂度都是 O(1)。
何为哈希表?
哈希表(Hash table)也被叫做散列表,它通过计算一个键值的映射函数(散列函数),将键(Key)映射到表中的一个位置,从而直接访问数据储存位置的数据结构,能带来极高的查询速度。
哈希算法是一种摘要算法,不同的数据产生定长的摘要,所以会产生碰撞冲突,为了解决数据冲突,会采用单独链表法
将散列到同一个存储位置的所有元素保存在一个链表中。
Sorted Set(有序集合)
有序集合和集合Set的特性基本相同,唯一的区别在于它是有序的。
每个字符串元素都与score
这个浮点数字值相关联。这个值就是它排序的分值(分值可以相同),根据这个分值实现元素的升序或降序排列。
适合的使用的场景:
- 排行榜
- 商品推荐
Hash(哈希)
Hash是一个由 字段
和 值
组成的映射表,也就是一个个键值对
,字段和值都是字符串类型,你可以把它想象成Java里的HashMap<String,String>,一个Key对应一个HashMap。
相对单独使用 键值对 保存数据而言,使用Hash类型来存储,更加节省空间。
适合的使用的场景:
- 购物车
- 对象属性信息
Bit Array(位数组)
Bit Array不是实际的数据类型,而是在String类型上定义的一组面向位的操作,所以可以说它是String类型的一种扩展。
由于字符串是二进制安全,并且最大长度为512 MB,因此它们适合设置多达 2的32次方 个不同的字节。
Bit Array就是一个长度可变的bit数组,每个位只能存储0或1。
位操作分为两类:
- 1,对单个位操作,把字段的某个位设置为 0或1
- 2,对给定的位范围内,统计其设置的位(0或1)的数量
所以,它的最大优点是:在存储信息时可以节省大量空间,例如,在以增量用户ID表示不同用户的系统中,仅使用512MB内存就可以记住40亿用户的位信息
适合的使用的场景:
- 数据去重
HyperLogLogs(概率数据结构)
HyperLogLogs是一种概率数据结构,用于对唯一元素进行计数(这里指集合的基数),它存在一定误差,但误差小于1%。
通常,对唯一元素进行计数需要保存元素本身,并使用与要计数的元素数量成比例的内存量。
而HyperLogLogs只需根据输入元素来计算基数,而不会储存输入元素本身,所以,无论元素的数量和体积有多大,计算基数所需的内存空间都是固定不变的,并且是很小,每个Key的占用内存不会超过12KB。
这个特性造就了它的价值,当然也丧失了获取元素的能力,不过获取元素的能力也不需要,所以根本不care。
相关命令:
命令 | 解释 | 示例 |
---|---|---|
pfadd | 添加一个或多个元素 | pfadd k a b c |
pfcount | 获取Key的基数估算值 | pfcount k |
pfmerge | 合并多个Key到一个新Key,如:将k1 与k2 合并到newk |
pfmerge newk k1 k2 |
示例:
1 | redis0> pfadd k a b c |
适合使用的场景:
- 记录网站访问量、PV、UV之类的数据
Stream(流)
Stream是Redis 5.0引入的新数据类型,它就像日志文件一样,仅以追加模式添加数据。
流与列表没有太大不同,只是附加的API更复杂,功能更强大。
它非常适合作为消息系统来使用,虽然 Redis 本身提供了发布订阅 (pub/sub) 来实现消息队列的功能,但是以前的发布订阅功能是有缺陷的,消息无法持久化,如果出现网络断开、Redis宕机等,消息就会被丢弃。
Stream流的工作方式截然不同,所有消息都将无限期保留在流中,除非用户明确要求删除,并且,丰富的API足以支撑整个消息系统的功能。
- 本文作者:沙果栗子本文链接:https://32e.co/2020/10/01/redis-data-types-intro/版权声明:本博客所有文章除特别声明外,均采用 CC BY-NC-SA 3.0 CN 许可协议。转载请注明出处!