Redis常用数据类型及操作详解

前言

这几年一直在it行业里摸爬滚打,一路走来,不少总结了一些python行业里的高频面试,看到大部分初入行的新鲜血液,还在为各样的面试题答案或收录有各种困难问题

于是乎,我自己开发了一款面试宝典,希望能帮到大家,也希望有更多的Python新人真正加入从事到这个行业里,让python火不只是停留在广告上。

微信小程序搜索:Python面试宝典

或可关注原创个人博客:https://lienze.tech

也可关注微信公众号,不定时发送各类有趣猎奇的技术文章:Python编程学习

Redis

Redis可以存储体与五种不同数据结构类型类型之间的映射

分别为STRING字符串、LIST列表、SET集合、HASH散列和ZSET有序集合

  • Redis客户端
redis-cli 
  • 如需支持中文展示,可以使用参数
redis-cli --raw

字符串(STRING)

redis中的字符串与很多语言中的字符串非常相似

字符串可以存储:字节串byte string、整数、浮点数

  • 常见指令
指令解释
GET获取存储在给定键中的值
SET设置存储在给定键中的值
DEL删除存储在给定键中的值
127.0.0.1:6379> set name 张三
OK
127.0.0.1:6379> get name
张三
127.0.0.1:6379> del name
1

列表(LIST)

一个列表结构可以有序的存储多个字符串

  • 常见指令、
指令解释
LPUSH/RPUSH将给定的值推入列表的左/右端
LPOP/RPOP从列表的左/右端弹出一个值并返回
LRANGE获取列表在给定范围内的值
LINDEX获取列表在某个给定位置上的值
127.0.0.1:6379> rpush l a
1
127.0.0.1:6379> rpush l b
2
127.0.0.1:6379> rpush l c
3
127.0.0.1:6379> lrange l 0 -1
a
b
c

rpush,是从列表的右侧推入数据,类似,后进入的数据在列表的头部

127.0.0.1:6379> lpush l1 a
1
127.0.0.1:6379> lpush l1 b
2
127.0.0.1:6379> lpush l1 c
3
127.0.0.1:6379> lrange l1 0 -1
c
b
a

lpush,是从列表的左侧推入数据,类似队列,先进的在头部

127.0.0.1:6379> lpush l1 a
1
127.0.0.1:6379> lpush l1 b
2
127.0.0.1:6379> lpush l1 c
3
127.0.0.1:6379> lrange l1 0 -1
c
b
a
127.0.0.1:6379> lindex l1 2
a

集合(SET)

Redis的集合和列表都可以存储多个字符串,但是不同在于列表可以存储多个相同的值,而集合中的数据元素是唯一的,这是由于集合通过散列表来进行维护(这些散列表只有键Key,没有与之相关的值Value

此外,redis中的结合是无序的,所以不能像列表一样的数据可以在某一端推入数据

指令解释
SADD将给定的元素添加到集合
SMEMBERS返回集合中包含的所有元素
SISMEMBER检查某元素是否包含在集合中
SREM如果元素存在与集合,那么移出该元素

**注意:**如果集合中包含的元素太多,那么SMEMBERS指令的处理可能会非常慢,慎用

127.0.0.1:6379> sadd s 1
1
127.0.0.1:6379> sadd s 2
1
127.0.0.1:6379> sadd s 3
1
127.0.0.1:6379> smembers s
1
2
3
127.0.0.1:6379> sismember s 2
1
127.0.0.1:6379> sismember s a
0
127.0.0.1:6379> srem s a
0
127.0.0.1:6379> srem s 1
1
127.0.0.1:6379> smembers s
2
3

一般情况下,命令的执行如果成功,那么将会返回对应操作生效的个数,比如:1,反之则返回0

散列(HASH)

散列可以存储多个键值对映射;散列存储的值可以是字符串、也可以是数字值

美妙的是,散列可以支持用户对其中存储的数字值进行自增或自减的操作

人们经常这样形容散列:这就像一个微缩版的Key-Value数据库,一个微缩版的Redis

指令解释
HSET在散列里面添加给定的键值对
HGET获取指定兼职对的值
HGETALL获取散列包含的所有键值对
HDEL如果给定的键存在与散列中,那么将其删除
127.0.0.1:6379> hset h k1 v1
1
127.0.0.1:6379> hset h k2 v2
1
127.0.0.1:6379> hget h k1
v1
127.0.0.1:6379> hdel h k1
1
127.0.0.1:6379> hgetall h
k2
v2

hgetall获取到的结果是竖着排列,两个为一组键值对

有序集合(ZSET)

有序集合和散列一样,都用于存储键值对

有序集合的键key是成员,在一个有序集合中,只能有一个不同的成员

有序集合的值是value被称为分值score,分值为一个浮点数类型,

有序集合通过分值对键值对进行排序

基于时间衰减的商品热度值计算

指令解释
ZADD将一个带有分值的成员添加到有序集合中
ZRANGE根据元素在有序排列中所处的位置,从有序集合中获取多个元素,类似lrange
ZRANGEBYSCORE获取有序集合中在给定分值范围内的成员
ZREM如果给定成员存在与有序集合中,那么移出这个成员
127.0.0.1:6379> ZADD z 5 first
(integer) 1
127.0.0.1:6379> ZADD z 3 second
(integer) 1
127.0.0.1:6379> ZRANGE z 0 -1
1) "second"
2) "first"
127.0.0.1:6379> ZRANGE z 0 -1 withscores
1) "second"
2) "3"
3) "first"
4) "5"
127.0.0.1:6379> ZADD z 4.5 third
(integer) 1
127.0.0.1:6379> ZRANGE z 0 -1 withscores
1) "second"
2) "3"
3) "third"
4) "4.5"
5) "first"
6) "5"
127.0.0.1:6379> zrem z third
(integer) 1
127.0.0.1:6379> ZRANGE z 0 -1 
1) "second"
2) "first"

字符串其他操作

自增、自减

当一个值被存入Redis时,如果这个值可以被解释成十进制或者浮点数,那么Redis会检测到这一属性

并允许用户可以对这样的值进行自增自减操作

指令解释
INCR将键存储的值增长1
DECR将键存储的值减去1
INCRBY将键存储的值加上整数
DECRBY将键存储的值减去整数
INCRBYFLOAT将键存储的值加上浮点数(传递负值即为减去)、在redis2.6及以上版本可用
127.0.0.1:6379> set age 1
OK
127.0.0.1:6379> incr age
(integer) 2
127.0.0.1:6379> get age
"2"
127.0.0.1:6379> decr age 
(integer) 1
127.0.0.1:6379> get age 
"1"

Python的代码中,只需要使用incr即可包含incrby的功能

127.0.0.1:6379> incrby age 10
(integer) 11
127.0.0.1:6379> get age 
"11"
127.0.0.1:6379> decrby age 5
(integer) 6
127.0.0.1:6379> get age 
"6"
127.0.0.1:6379> incrbyfloat age -2.5
"3.5"
子串

python的切片操作一样,Redis中的字符串也支持对某个范围进行操作

指令解释
APPEND将一个值追加到给定字符串的末尾
GETRANGE给定起点、终点,获取该范围内所有的字符组成的子串,包括起点重点,左闭右闭
SETRANGE将字符串从某个偏移量开始设置成给定的值
127.0.0.1:6379> set name abc
OK
127.0.0.1:6379> append name aaa
(integer) 6
127.0.0.1:6379> get name 
"abcaaa"

现在版本的getrange是由老版本的substr函数改名而来,如果使用2.6版本以上的redis,建议使用getrange

127.0.0.1:6379> getrange name 2 4
"caa"
127.0.0.1:6379> substr name 2 4
"caa"
# 左闭右闭
127.0.0.1:6379> getrange name 0 -1
"abcaaa"
127.0.0.1:6379> setrange name 2 ***
(integer) 6
127.0.0.1:6379> get name
"ab***a"

列表其他操作

范围裁剪

除了以上对于列表某个位置或范围的访问,以及对列表左或右侧推入、弹出数据的命令

还可以通过LTRIM对列表进行裁剪

指令解释
LTRIM给定起点和终点,对列表进行裁剪,只保留该范围内的数据
# l: 4, 3, 2, 1
127.0.0.1:6379> ltrim l 1 3
OK
127.0.0.1:6379> lrange l 0 -1
1) "2"
2) "1"
元素移动

redis还支持在两个列表之间进行数据移动,从某个列表中pop数据,然后push到另外一个列表中

指令解释
RPOPLPUSH source dest从source列表中弹出最右端的数据,并从最左端推入dest列表中
BRPOPLPUSH source dest timeouttimeout参数代表当source列表为空时,该命令阻塞等待可弹出数据,超过时间则返回None
# l1: 2,1 
# l2: a,
127.0.0.1:6379> lrange l1 0 -1
1) "2"
127.0.0.1:6379> lrange l2 0 -1
1) "1"
2) "a"
阻塞弹出
指令解释
BLPOP阻塞等待timeout时间,从一个非空列表中弹出最左侧的元素,超时返回None
BRPOP与上同,只是从列表的最右侧弹出元素

这俩命令本质上与普通的LPOPRPOP差不多,只是多了阻塞行为

集合其他操作

计数、随机

唯一、无序

指令解释
SCARD返回集合中包含元素的数量
SRANDMEMBER KEY COUNT从key的集合中随机返回COUNT个数量的元素
SPOP KEY COUNT随机移除COUNT个元素,并返回被移除的元素
127.0.0.1:6379> smembers s1
1) "1"
2) "2"
3) "3"
127.0.0.1:6379> scard s1
(integer) 3
127.0.0.1:6379> srandmember s1 2
1) "2"
2) "1"
127.0.0.1:6379> srandmember s1 2
1) "2"
2) "3"
127.0.0.1:6379> spop s1 2
1) "2"
2) "3"
127.0.0.1:6379> smembers s1
1) "1"
组合
指令解释
SMOVE SOURCE DEST ITEM如果ITEM存在与SOURCE中,那么将其移除并添加到DEST集合中,成功返回1,反之返回0
127.0.0.1:6379> sadd s1 a
(integer) 1
127.0.0.1:6379> sadd s2 * 
(integer) 1
127.0.0.1:6379> smove s1 s2 a
(integer) 1
127.0.0.1:6379> smove s1 s2 a
(integer) 0
127.0.0.1:6379> smembers s2
1) "*"
2) "a"
127.0.0.1:6379> smembers s1
(empty list or set)
差集、交集、并集

与数学中的语义一致

指令解释
SDIFF KEY1 KEY2…返回存在与KEY1而不存在于其他集合中的元素(差集)
SDIFFSTORE DEST KEY1 KEY2…返回存在与KEY1而不存在于其他集合中的元素(差集),并存储到DEST
SINTER KEY1 KEY2…返回同时存在于所有集合中的元素(交集)
SINTERSTORE DEST KEY1 KEY2…返回同时存在于所有集合中的元素(交集),并存储到DEST
SUNION KEY1 KEY2…返回那些至少存在于一个集合中的元素(并集)
SUNIONSTORE DEST KEY1 KEY2返回那些至少存在于一个集合中的元素(并集),并存储到DEST
127.0.0.1:6379> sdiffstore dest s2 s1
(integer) 2
127.0.0.1:6379> smembers dest
1) "*"
2) "a"
# dest: *, a
# s2: *, a
# s3: ~
127.0.0.1:6379> sunion dest s2
1) "*"
2) "a"
127.0.0.1:6379> sunion dest s2 s3
1) "*"
2) "~"
3) "a"

散列其他操作

批量存储

之前的是单独的keyvalue存储

来看看更高级的批量键值获取存储,这样的操作可以减少命令的调用次数,以及客户端与Redis之间的通信往返次数来提升Redis的性能

指令解释
HMGET从一个散列获取一个或多个值
HMSET为散列设置一个或多个值
HLEN返回散列包含的键值对数量
127.0.0.1:6379> hmset hm a 1 b 2 c 3
OK
127.0.0.1:6379> hmget hm a b c
1) "1"
2) "2"
3) "3"
127.0.0.1:6379> hlen hm
(integer) 3
获取、检查

Redis的散列还可以像Python中的字典一样,支持集成了很多功能

指令解释
HEXISTS检查给定的键是否在散列中
HKEYS获取散列包含的所有键
HVALS获取散列包含的所有值
HINCRYBY将键存储的值加上一个整数
HINCRYBYFLOAT将键存储的值加上一个浮点数
127.0.0.1:6379> hset h a 1
(integer) 1
127.0.0.1:6379> hexists h a 
(integer) 1
127.0.0.1:6379> hexists h b
(integer) 0
# h: { 1:a, 2:b }
127.0.0.1:6379> hvals h
1) "v2"
2) "1"
3) "2"
127.0.0.1:6379> hkeys h
1) "k2"
2) "a"
3) "b"

使用getall在大量数据的情况下,可以先使用hkeys,然后再使用hget一个个的取出键的值

有序集合其他操作

计数、区间

有序集合主要是通过分值大小有序的进行获取和扫描成员

指令解释
ZCARD返回有序集合的数据成员数量
ZINCRBY将有序集合某个成员的分值加上某个值
ZCOUNT KEY MIN MAX返回分值介于min和max之间的成员数量
ZRANK KEY MEMBER返回成员在有序集合中的排名
ZSCORE返回成员的分值
127.0.0.1:6379> zcard z
(integer) 2
# a2:5 a3:7 a1:10
127.0.0.1:6379> zadd z 10 a1
(integer) 1
127.0.0.1:6379> zadd z 5 a2
(integer) 1
127.0.0.1:6379> zadd z 7 a3
(integer) 1
127.0.0.1:6379> zrange z 0 -1
1) "a2"
2) "a3"
3) "a1"
127.0.0.1:6379> zcount z 7 10
(integer) 2
127.0.0.1:6379> zrank z a2
(integer) 0
127.0.0.1:6379> zrank z a3
(integer) 1
127.0.0.1:6379> zrank z a1
(integer) 2
127.0.0.1:6379> zscore z a1
"10"
范围删除、获取

除了正向的排序,还可以通过分值逆向排序提取结果

还可以对有序集合进行范围移除

指令解释
ZREVRANK返回从大到小的单个元素的排名
ZREVRANGE返回有序集合给定排名范围内的成员,成员按照分值从大到校排列
ZRANGEBYSCORE KEY MIN MAX返回介于某个分值之间的所有元素
ZREVRANGEBYSCORE返回介于某个分值之间的所有元素并逆序
ZREMRANGEBYRANK KEY START STOP移除介于某个排名区间之间的所有元素
ZREMRANGEBYSCORE KEY MIN MAX移除介于某个分值之间的所有元素
ZINTERSTORE执行交集运算
ZUNIONSTORE执行并集运算
127.0.0.1:6379> zrange z 0 -1
1) "a2"
2) "a3"
3) "a1"
127.0.0.1:6379> zrevrank z a3
(integer) 1
127.0.0.1:6379> zrevrank z a2 
(integer) 2
127.0.0.1:6379> zrevrank z a1
(integer) 0
127.0.0.1:6379> zrevrange z1 0 -1
1) "zhangsan"
2) "wangwu"
3) "lisi"
127.0.0.1:6379> zrange z1 0 -1
1) "lisi"
2) "wangwu"
3) "zhangsan"
127.0.0.1:6379> zrangebyscore z1 99.5 100
1) "wangwu"
2) "zhangsan"
127.0.0.1:6379> zremrangebyrank z1 0 1
(integer) 2
127.0.0.1:6379> zrange  z1 0 1
1) "zhangsan"
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

李恩泽的技术博客

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值