开启运维之路之第 6 篇——Redis五种数据类型string、list、hash、set、zset

版权声明: https://blog.csdn.net/BiandanLoveyou/article/details/81201921

1、上一篇介绍Redis的基础,提供2种启动方式,这里汇总一下:

①写 shell 脚本,运行 shell 脚本。详见上一篇文章结尾。

②[root@localhost ~]# cd /usr/local/redis/

[root@localhost redis]# ./bin/redis-server ./redis.conf

校验是否启动方式:

[root@localhost redis]# ps -ef | grep -i redis
或者看下能否ping通:

[root@localhost redis]# ./bin/redis-cli
127.0.0.1:6379> ping
PONG
127.0.0.1:6379> 

停止服务:[root@localhost redis]# ./bin/redis-cli shutdown

以下字符串的学习,都需要进入到 redis 客户端。命令如上面所述,进入到redis客户端:

[root@localhost redis]# ./bin/redis-cli
127.0.0.1:6379>

2、Redis数据类型之字符串类型——string

string 常用功能:①设置值;②取值;③删除;④数值增、减;⑤其它扩展  (忽略大小写,SET、set、Set 都可以)

①设置值:set key value 设定指定 key 的值

②取值:get key  获取指定 key 的值

127.0.0.1:6379> set myKey biandanLoveYou
OK
127.0.0.1:6379> get myKey
"biandanLoveYou"

③删除:del key 删除指定 key 的值

127.0.0.1:6379> del myKey
(integer) 1
127.0.0.1:6379> get myKey
(nil)

④数值增、减:

incr key 自增,假如没有定义,则默认从 0 开始;非数值类型会报错。

127.0.0.1:6379> incr n
(integer) 1
127.0.0.1:6379> get n
"1"

下面演示数值自增、非数值报错的例子:

数值自增:

127.0.0.1:6379> set n1 5
OK
127.0.0.1:6379> incr n1
(integer) 6
127.0.0.1:6379> get n1
"6"

非数值自增会报错:

127.0.0.1:6379> set n2 boy
OK
127.0.0.1:6379> incr n2
(error) ERR value is not an integer or out of range

自减:decr key 假如没有定义,则默认从 0 开始;非数值类型会报错。

127.0.0.1:6379> decr m
(integer) -1
127.0.0.1:6379> get m
"-1"
127.0.0.1:6379> decr n1
(integer) 5
127.0.0.1:6379> get n1
"5"
127.0.0.1:6379> decr n2
(error) ERR value is not an integer or out of range

tip:一般设置商品的数量,会存入 redis ,用户购买1个,自减1。

string 扩展命令:

incrby key number 指定增值量;decrby key number 指定减少量;append key str 追加字符串。

127.0.0.1:6379> get m
"4"
127.0.0.1:6379> incrby m 5
(integer) 9
127.0.0.1:6379> get m
"9"
127.0.0.1:6379> decrby m 2
(integer) 7
127.0.0.1:6379> get m
"7"
127.0.0.1:6379> get n2
"boy"
127.0.0.1:6379> append n2 girl
(integer) 7
127.0.0.1:6379> get n2
"boygirl"

3、Redis数据类型之列表——list (百度百科上称之为:双向列表)

Redis列表是简单的字符串列表,按照插入顺序排序。你可以添加一个元素到列表的头部(左边)或者尾部(右边)
一个列表最多可以包含 232 - 1 个元素 (4294967295, 每个列表超过40亿个元素)。

可以这样理解 list :从右边往左边开的火车,左边是车头,右边是车尾。

常用命令:两端添加;两端弹出;扩展命令

①两端添加:

左边添加:lpush key value,lpush(left push的意思)注意,是从左端开始添加,下一个添加的元素会排在上一个的左边,把上一个元素挤在右边。最后添加的元素,把其它元素都挤在右边了。一般很少使用从左边添加。因为左边默认是车头。

127.0.0.1:6379> lpush myList1 a b c d haha
(integer) 5
127.0.0.1:6379> lpush myList1 1 2 5 88 90
(integer) 10

注意,每种数据类型都有其添加、获取、删除的命令,打比方:不能使用 get 命令来获取 list

127.0.0.1:6379> get myList1
(error) WRONGTYPE Operation against a key holding the wrong kind of value

要获取 list 集合,从左边位置开始获取,使用:lrange key start stop (left range的意思)其中:start是开始位置,stop是结束位置,-1是长度-1,与Java的for循环list一样。

127.0.0.1:6379> lrange myList1 0 -1
 1) "90"
 2) "88"
 3) "5"
 4) "2"
 5) "1"
 6) "haha"
 7) "d"
 8) "c"
 9) "b"
10) "a"

list 没有数组越界的概念,比如 stop 的数值可以比 list 的长度大,这样会获取所有的 list 数据:

127.0.0.1:6379> lrange myList1 0 20

127.0.0.1:6379> lrange myList1 0 20
 1) "90"
 2) "88"
 3) "5"
 4) "2"
 5) "1"
 6) "haha"
 7) "d"
 8) "c"
 9) "b"
10) "a"

右端添加(大多数人使用):rpush key value,rpush(right push的意思)如:127.0.0.1:6379> rpush myList1 boy girl

127.0.0.1:6379> lrange myList1 0 -1
 1) "90"
 2) "88"
 3) "5"
 4) "2"
 5) "1"
 6) "haha"
 7) "d"
 8) "c"
 9) "b"
10) "a"
11) "boy"
12) "girl"

②获取 list 列表的长度:llen key

127.0.0.1:6379> llen myList1
(integer) 12

③通过索引获取数据:lindex key

127.0.0.1:6379> lindex myList1 2
"5"

④从左端移出并获取列表的第 1 个元素lpop key
先创建一个测试的list,添加元素:

127.0.0.1:6379> lpush myList2  11 22 33 boy friend
(integer) 5
127.0.0.1:6379> lrange myList2 0 -1
1) "friend"
2) "boy"
3) "33"
4) "22"
5) "11"

然后执行移出并获取左端的1个元素(即最后添加的元素,其它元素都被最后一个元素挤在右边了):

127.0.0.1:6379> lpop myList2
"friend"
127.0.0.1:6379> lrange myList2 0 -1
1) "boy"
2) "33"
3) "22"
4) "11"

结果发现: friend 元素被移出,并且获取了它。

⑤从右端移出并获取列表的第 1 个元素:rpop key

127.0.0.1:6379> rpop myList2
"11"
127.0.0.1:6379> lrange myList2 0 -1
1) "boy"
2) "33"
3) "22"

⑥集合的头部、尾部添加元素:lpushx key value1 value2...      rpushx key value1 value2 ...

127.0.0.1:6379> lpushx myList2 good
(integer) 4
127.0.0.1:6379> rpushx myList2 bad
(integer) 5
127.0.0.1:6379> lrange myList2 0 -1
1) "good"
2) "boy"
3) "33"
4) "22"
5) "bad"

⑦从指定方向删除集合元素: lrem key count value,特别注意这个 count

先添加一个测试的集合 myList3

127.0.0.1:6379> lpush myList3 2 4 6 8 1 8 6 4 2
(integer) 9
127.0.0.1:6379> lrange myList3 0 -1
1) "2"
2) "4"
3) "6"
4) "8"
5) "1"
6) "8"
7) "6"
8) "4"
9) "2"

左边开始,删除 2 个 6:lrem myList3 2 6

127.0.0.1:6379> lrem myList3 2 6
(integer) 2
127.0.0.1:6379> lrange myList3 0 -1
1) "2"
2) "4"
3) "8"
4) "1"
5) "8"
6) "4"
7) "2"

说明:左边开始,count为正整数;右边开始,count为负整数。0 表示删除所有

右边开始,删除 1 个 4:lrem myList3 -1 4

127.0.0.1:6379> lrem myList3 -1 4
(integer) 1
127.0.0.1:6379> lrange myList3 0 -1
1) "2"
2) "4"
3) "8"
4) "1"
5) "8"
6) "2"

删除所有的 1:lrem myList3 0 1

127.0.0.1:6379> lrem myList3 0 1
(integer) 1
127.0.0.1:6379> lrange myList3 0 -1
1) "2"
2) "4"
3) "8"
4) "8"
5) "2"

⑧设置集合元素的值:lset key index value 。注意索引是从 0 开始。与 Java 的 list 、数组的集合从 0 开始性质一样。

127.0.0.1:6379> lset myList3 2 66
OK
127.0.0.1:6379> lrange myList3 0 -1
1) "2"
2) "4"
3) "66"
4) "8"
5) "2"

这样,原来在第 3 个位置的 8 就变成了 66 。

⑨在指定元素之前、之后添加元素:linsert key before|after pivot value

127.0.0.1:6379> linsert myList3 before 66 boy
(integer) 6
127.0.0.1:6379> linsert myList3 after 4 girl
(integer) 7
127.0.0.1:6379> lrange myList3 0 -1
1) "2"
2) "4"
3) "girl"
4) "boy"
5) "66"
6) "8"
7) "2"

把A集合尾部元素弹出并插入到B集合头部:rpoplpush sourceList descList

127.0.0.1:6379> rpoplpush myList2 myList3
"bad"
127.0.0.1:6379> lrange myList3 0 -1
1) "bad"
2) "2"
3) "4"
4) "girl"
5) "boy"
6) "66"
7) "8"
8) "2"

4、Redis数据类型之哈希——hash

Redis hash 是一个string类型的field和value的映射表,hash特别适合用于存储对象。
Redis 中每个 hash 可以存储 232 - 1 键值对(40多亿)。

hash常用命令:赋值、取值、删除、增加数字、判断字段是否存在、获取hash属性个数、获取hash所有属性名称。

①赋值、取值:hset key field value  ;  hget key field

127.0.0.1:6379> hset h1 username biandan
(integer) 1
127.0.0.1:6379> hget h1 username
"biandan"

多个字段一起设置值、取值:hmset key field1 value1 field2 value2 ...    hmget key field1 field2 

127.0.0.1:6379> hmset h2 username Hello password 123
OK
127.0.0.1:6379> hmget h2 username password
1) "Hello"
2) "123"

②获取 hash 中指定 key 的所有字段和值:hgetall key

127.0.0.1:6379> hgetall h2
1) "username"
2) "Hello"
3) "password"
4) "123"

③删除属性,可以一次性删除多个:hdel key field1 field2 ...

127.0.0.1:6379> hdel h2 username password
(integer) 2
127.0.0.1:6379> hgetall h2
(empty list or set)

④增加数字:hincrby key field count

127.0.0.1:6379> hset h3 age 15
(integer) 1
127.0.0.1:6379> hincrby h3 age 5
(integer) 20
127.0.0.1:6379> hget h3 age
"20"

⑤判断字段是否存在:存在 1 ,不存在 0 :hexists key field

127.0.0.1:6379> hexists h3 age
(integer) 1
127.0.0.1:6379> hexists h3 tall
(integer) 0

⑥获取字段数量:hlen key

127.0.0.1:6379> hlen h3
(integer) 1

⑦获取所有属性名(字段名):hkeys key

127.0.0.1:6379> hkeys h1
1) "username"
127.0.0.1:6379> hkeys h2
(empty list or set)

⑧获取所有属性值:hvals key

127.0.0.1:6379> hvals h1
1) "biandan"
127.0.0.1:6379> hvals h2
(empty list or set)

5、Redis数据类型之集合——set

Redis 的 Set 是 String 类型的无序集合。集合成员是唯一的,这就意味着集合中不能出现重复的数据。
Redis 中集合是通过哈希表实现的,所以添加,删除,查找的复杂度都是 O(1)。
集合中最大的成员数为 232 - 1 (4294967295, 每个集合可存储40多亿个成员)。

set常用命令:
添加/删除元素,获取集合中的元素,集合中的并、交、差集运算,扩展命令

①添加、获取、删除元素:sadd key value1 value2 ...   smembers key     srem key value1 value2 ...

注意:set 不允许有重复元素出现,不会重复添加重复元素。

127.0.0.1:6379> sadd s1 n b a 1 2 5
(integer) 6
127.0.0.1:6379> smembers s1
1) "b"
2) "n"
3) "1"
4) "a"
5) "5"
6) "2"
127.0.0.1:6379> sadd s1 c b a
(integer) 1
127.0.0.1:6379> smembers s1
1) "c"
2) "a"
3) "b"
4) "1"
5) "n"
6) "5"
7) "2"
127.0.0.1:6379> srem s1 b
(integer) 1
127.0.0.1:6379> smembers s1
1) "c"
2) "a"
3) "1"
4) "n"
5) "5"
6) "2"

②判断某个元素是否存在,存在 1 ,不存在 0 :sismember key field

127.0.0.1:6379> sismember s1 n
(integer) 1
127.0.0.1:6379> sismember s1 b
(integer) 0

③计算元素总数:scard key

127.0.0.1:6379> scard s1
(integer) 6

④计算并、交、差 集:

先新增 s2 做测试

127.0.0.1:6379> sadd s2 n c a a 5 8
(integer) 5
127.0.0.1:6379> smembers s1
1) "c"
2) "a"
3) "1"
4) "n"
5) "5"
6) "2"
127.0.0.1:6379> smembers s2
1) "a"
2) "c"
3) "5"
4) "n"
5) "8"

并集:sunion key1 key2

127.0.0.1:6379> sunion s1 s2
1) "c"
2) "a"
3) "8"
4) "1"
5) "n"
6) "2"
7) "5"

交集:sinter key1 key2

127.0.0.1:6379> sinter s1 s2
1) "a"
2) "c"
3) "5"
4) "n"

差集:sdiff key1 key2     注意:差集以 key1 (前者) 为参考。

127.0.0.1:6379> sdiff s1 s2
1) "1"
2) "2"
127.0.0.1:6379> sdiff s2 s1
1) "8"

⑤把并、交、差 集存入新的集合

并集存入新集合:sunionstore resultSet key1 key2

127.0.0.1:6379> sunionstore sr3 s1 s2
(integer) 7
127.0.0.1:6379> smembers sr3
1) "c"
2) "a"
3) "8"
4) "1"
5) "n"
6) "2"
7) "5"

交集存入新集合:sinterstore resultSet key1 key2

127.0.0.1:6379> sinterstore sr2 s1 s2
(integer) 4
127.0.0.1:6379> smembers sr2
1) "a"
2) "c"
3) "5"
4) "n"

差集存入新集合:sdiffstore resultSet key1 key2

127.0.0.1:6379> sdiffstore sr1 s1 s2
(integer) 2
127.0.0.1:6379> smembers sr1
1) "1"
2) "2"

存储Set使用场景: 跟踪一些唯一性数据,用于维护数据对象之间的关联关系。

6、Redis数据类型之有序集合——zset

Redis 有序集合和集合一样也是string类型元素的集合,且不允许重复的成员。
不同的是每个元素都会关联一个double类型的分数。redis正是通过分数来为集合中的成员进行从小到大的排序。
有序集合的成员是唯一的,但分数(score)却可以重复。
集合是通过哈希表实现的,所以添加,删除,查找的复杂度都是O(1)。 
集合中最大的成员数为 232 - 1 (4294967295, 每个集合可存储40多亿个成员)。

Sorted-Set使用场景:
大型在线游戏积分排行榜
构建索引数据

①添加元素、查询元素:zadd key score1 field1 score2 field2   ;  zrange key start stop

127.0.0.1:6379> zadd z1 8 aa 5 bb 2 cc
(integer) 3
127.0.0.1:6379> zrange z1 0 -1
1) "cc"
2) "bb"
3) "aa"

说明:添加集合 z1 ,元素是 aa,bb和cc,评分是8,5和2,评分在前,元素在后。

集合里的排序是根据评分从小到大排序的,所以输出的时候评分小的输出在前。

重复添加元素:有则覆盖,没有则新增。例子中,aa已经存在,覆盖;dd没有,新增。

127.0.0.1:6379> zadd z1 25 aa
(integer) 0
127.0.0.1:6379> zadd z1 35 dd
(integer) 1
127.0.0.1:6379> zrange z1 0 -1
1) "cc"
2) "bb"
3) "aa"
4) "dd"

之前aa的评分是8,现在看aa的评分是否是25:zscore key filed

127.0.0.1:6379> zscore z1 aa
"25"

是25,证明是被覆盖了。

②删除元素:zrem key field

127.0.0.1:6379> zrem z1 bb
(integer) 1
127.0.0.1:6379> zrange z1 0 -1
1) "cc"
2) "aa"
3) "dd"

③查看集合里元素个数:zcard key field

127.0.0.1:6379> zcard z1
(integer) 3

查看元素,包括评分也列出来:

127.0.0.1:6379> zrange z1 0 -1 withscores
1) "cc"
2) "2"
3) "aa"
4) "25"
5) "dd"
6) "35"

④降序排序输出:zrevrange key start stop withscores   (说明:reverse是反向的意思)

127.0.0.1:6379> zrevrange z1 0 -1 withscores
1) "dd"
2) "35"
3) "aa"
4) "25"
5) "cc"
6) "2"

添加几个测试元素:

127.0.0.1:6379> zadd z1 3 y 5 n 30 w 18 q
(integer) 4
127.0.0.1:6379> zrange z1 0 -1 withscores
 1) "cc"
 2) "2"
 3) "y"
 4) "3"
 5) "n"
 6) "5"
 7) "q"
 8) "18"
 9) "aa"
10) "25"
11) "w"
12) "30"
13) "dd"
14) "35"

根据评分范围来查找元素:zrangebyscore key score1 score2 withscores

127.0.0.1:6379> zrangebyscore z1 10 20 withscores
1) "q"
2) "18"

限定查找起始,类似分页:zrangebyscore key score1 score2 withscores limit start stop

127.0.0.1:6379> zrangebyscore z1 2 20 withscores limit 0 3
1) "cc"
2) "2"
3) "y"
4) "3"
5) "n"
6) "5"

查找指定评分范围的元素个数:zcount key start stop

127.0.0.1:6379> zcount z1 3 30
(integer) 5

给指定元素加分:zincrby key score field

127.0.0.1:6379> zincrby z1 13 cc
"15"

根据排名来删除元素,删除2个:zremrangebyrank key start stop  (从 0 开始计算)

127.0.0.1:6379> zremrangebyrank z1 0 1
(integer) 2
127.0.0.1:6379> zrange z1 0 -1 withscores
 1) "cc"
 2) "15"
 3) "q"
 4) "18"
 5) "aa"
 6) "25"
 7) "w"
 8) "30"
 9) "dd"
10) "35"

根据具体评分范围来删除元素:zremrangebyscore key start stop

127.0.0.1:6379> zremrangebyscore z1 10 20
(integer) 2
127.0.0.1:6379> zrange z1 0 -1 withscores
1) "aa"
2) "25"
3) "w"
4) "30"
5) "dd"
6) "35"

猜你喜欢

转载自blog.csdn.net/BiandanLoveyou/article/details/81201921