文章目录
前言
本篇文章主要介绍了 redis 几种数据类型的简单操作和使用场景。
提示:以下是本篇文章正文内容,下面案例可供参考
一、Redis 简介与安装
Redis 是完全开源的,遵守 BSD 协议,是一个高性能的 key-value 的 no-sql(非关系型) 数据库。
cd /usr/local/src
wget http://download.redis.io/releases/redis-5.0.5.tar.gz
tar -zxvf redis-5.0.5.tar.gz
cd redis-5.0.5
make
make install
cd /usr/local/bin
ls
// 查看是否有redis-server redis-cli,若没有则执行如下两行命令
cp /app/src/redis-5.0.5/src/redis-server /usr/local/bin
cp /app/src/redis-5.0.5/src/redis-cli /usr/local/bin
修改redis.conf文件
将 daemonize no 改为 daemonize yes //允许后台运行redis服务 默认端口6379
#requirepass foobared去掉注释,foobared改为自己的密码,我在这里改为123,requirepass 123 //可以修改redis密码
bind 127.0.0.1,修改为bind 0.0.0.0 //允许外部网络连接
esc进入命令模式输入:wq保存;命令模式下输入/关键字可快速查找关键字n切换至下一个匹配的关键字
./redis-server /usr/local/src/redis-5.0.5/redis.conf //指定redis.conf文件启动
二、Redis 数据类型
Redis 支持五种数据类型:string(字符串),hash(哈希),list(列表),set(集合)及 zsetsorted set:(有序集合)。
命令参考:http://doc.redisfans.com/
1.string 字符串
使用场景:
- 计数器(incr、decr)
- 分布式锁(set key value nx ex seconds)
- 存储对象(不经常变化的 set key value-json)
SET key value [EX seconds] [PX milliseconds] [NX|XX]
命令 SET resource-name anystring NX EX max-lock-time 是一种在 Redis 中实现锁的简单方法。
参数 | 解释 |
---|---|
EX second | 设置键的过期时间为 second 秒。 SET key value EX second 效果等同于 SETEX key second value 。 |
PX milliseconds | 设置键的过期时间为 millisecond 毫秒。SET key value PX millisecond 效果等同于 PSETEX key millisecond value 。 |
NX | 只在键不存在时,才对键进行设置操作。 SET key value NX 效果等同于 SETNX key value 。 |
XX | 只在键已经存在时,才对键进行设置操作。 |
#查看所有的key
127.0.0.1:6379> keys *
#查看的key过期时间
127.0.0.1:6379> ttl key
# EXISTS key 检查给定 key 是否存在。
127.0.0.1:6379> set name alpari
OK
127.0.0.1:6379> get name
"alpari"
#在遇到数值操作时,redis会将字符串类型转换成数值。
127.0.0.1:6379> set num "2"
#将 key 中储存的数字值增一。由于INCR等指令本身就具有原子操作的特性,所以我们完全可以利用redis的incr、incrby、decr、decrby等指令来实现原子计数的效果
127.0.0.1:6379> incr num //get num -- 3
(integer) 3
#将值 value 关联到 key ,并将 key 的过期时间设为 seconds (以秒为单位)。
127.0.0.1:6379> setex key seconds value
#只有在 key 不存在时设置 key 的值。
127.0.0.1:6379> setnx key value
# MGET key [key ...] 返回所有(一个或多个)给定 key 的值。
# MSET key value [key value ...] 同时设置一个或多个 key-value 对。
# SETRANGE key offset value 用 value 参数覆写(overwrite)给定 key 所储存的字符串值,从偏移量 offset 开始。类似Java替换字符串。
# STRLEN key 返回 key 所储存的字符串值的长度。
2.list 列表
使用场景:
- 队列(lpush 和 rpop)、秒杀抢购
- 排行榜(定时计算 rpush 和 lrange)
127.0.0.1:6379[2]> lpush mykey v1 v1 v3 # 将一个或多个值 value 插入到列表 key 的表头
# RPUSH key value [value ...] 将一个或多个值 value 插入到列表 key 的表尾(最右边)。
127.0.0.1:6379[2]> lrange mykey 0 -1 # 查询,列表允许重复元素
1) "v3"
2) "v1"
3) "v1"
127.0.0.1:6379[2]> lpop mykey # 移除并返回列表 key 的头元素。
"v3"
127.0.0.1:6379[2]> lrange mykey 0 -1
1) "v2"
2) "v1"
127.0.0.1:6379[2]> rpop mykey # 移除并返回列表 key 的尾元素。
"v1"
127.0.0.1:6379[2]> lrange mykey 0 -1
1) "v2"
3.hash 散列
使用场景:
- 购物车(hmset user:id product:id 2)(hmset key field value)
- 存储对象(频繁修改的属性 hest)
127.0.0.1:6379[2]> flushdb # 清空当前db,flushall清空所有
OK
127.0.0.1:6379[2]> hset mykey name alpari # 将哈希表 key 中的域 field 的值设为 value 。
(integer) 1 # 如果 key 不存在,一个新的哈希表被创建并进行 HSET 操作。并返回 1
127.0.0.1:6379[2]> hget mykey name
"alpari"
127.0.0.1:6379[2]> hset mykey name alpariwang
(integer) 0 # 如果域 field 已经存在于哈希表中,旧值将被覆盖。并返回 0
127.0.0.1:6379[2]> hget mykey name
"alpariwang"
########################
127.0.0.1:6379[2]> hmset mykey age 1 sex 0 # 设置多个
OK
127.0.0.1:6379[2]> hmget mykey age sex # 查看多个
1) "1"
2) "0"
##########################
127.0.0.1:6379[2]> hgetall mykey # 用于返回哈希表中,所有的字段和值;hvals 命令,用于返回哈希表所有 field 对应的值。
1) "name" # key
2) "alpariwang" # value
3) "age"
4) "22"
5) "sex"
6) "0"
127.0.0.1:6379[2]> hdel mykey sex age # 删除多个field
(integer) 2
127.0.0.1:6379[2]> hgetall mykey
1) "name"
2) "alpariwang"
4.set 集合
使用场景:
- 抽奖(srandmember 重复、spop 不重复)
- 点赞(srem 取消、scard 获赞人数、sismember 是否点赞)、收藏
- 共同好友功能,共同喜好(sdiff、sinter、sunion)
- 实时统计网站的独立IP(元素不唯一)
127.0.0.1:6379[2]> sadd user:1 1001 1002 1003 1001 1004 # 添加多个不重复的元素
(integer) 4
127.0.0.1:6379[2]> scard user:1 # 返回集合 key 的基数(集合中元素的数量)。
(integer) 4
127.0.0.1:6379[2]> sadd user:2 1003 1004 1005 1006
(integer) 4
127.0.0.1:6379[2]> sdiff user:1 user:2 # 返回差集
1) "1001"
2) "1002"
127.0.0.1:6379[2]> sinter user:1 user:2 # 返回交集
1) "1003"
2) "1004"
127.0.0.1:6379[2]> sunion user:1 user:2 # 返回并集
1) "1001"
2) "1002"
3) "1003"
4) "1004"
5) "1005"
6) "1006"
127.0.0.1:6379[2]> sismember user:1 1002 # 判断元素是否是集合成员,1 是 0 不是
(integer) 1
127.0.0.1:6379[2]> smembers user:1 # 返回集合所有成员
1) "1001"
2) "1002"
3) "1003"
4) "1004"
127.0.0.1:6379[2]> smove user:1 user:2 1004 # 将集合1的元素移到集合2中
(integer) 1
127.0.0.1:6379[2]> spop user:1 1 # 移除并返回集合中的一个随机元素。
1) "1003"
127.0.0.1:6379[2]> srandmember user:2 # 返回集合中一个或多个随机数
"1006"
127.0.0.1:6379[2]> srem user:1 1002 # 移除元素
(integer) 1
127.0.0.1:6379[2]> smembers user:1
1) "1001"
5.zset 有序集合
使用场景:
- 延时队列
- 排行榜(zadd class:score:id 60 xiaoming…zrevrangebyscore)
- 限流-滑动窗口(https://zhuanlan.zhihu.com/p/147912757)
127.0.0.1:6379[2]> zadd scores 50 libai 60 fei 80 zhuge 90 waner # 添加元素
(integer) 4
127.0.0.1:6379[2]> zcard scores # 返回有序集 key 的基数
(integer) 4
127.0.0.1:6379[2]> zcount scores 50 70 # 返回有序集 key 中, score 值在 min 和 max 之间(包含)的成员的数量。
(integer) 2
127.0.0.1:6379[2]> zincrby scores 5 fei # 有序集合中对指定成员的分数加上增量5
"65"
127.0.0.1:6379[2]> zrange scores 0 -1 withscores # 返回有序集 key 中,指定区间内的成员。
1) "libai"
2) "50"
3) "fei"
4) "65"
5) "zhuge"
6) "80"
7) "waner"
8) "90"
127.0.0.1:6379[2]> zrangebyscore scores 60 80 withscores
# 返回有序集 key 中,所有 score 值介于 min 和 max 之间(包括等于 min 或 max )的成员。有序集成员按 score 值递增(从小到大)次序排列。
1) "fei"
2) "65"
3) "zhuge"
4) "80"
127.0.0.1:6379[2]> zrem scores libai # 移除
(integer) 1
127.0.0.1:6379[2]> zscore scores waner # 返回有序集中,成员的分数值
"90"
127.0.0.1:6379[2]> zrevrank scores waner # 返回有序集合中指定成员的排名 从 0 开始
(integer) 0
127.0.0.1:6379[2]> zrevrangebyscore scores +inf -inf withscores # 排名
1) "waner"
2) "90"
3) "zhuge"
4) "80"
5) "fei"
6) "65"
127.0.0.1:6379[2]> zrevrangebyscore scores +inf -inf withscores limit 0 1
1) "waner"
2) "90"
6.geo 存储地理位置信息
使用场景:
- 附近的人
# 添加地理位置的坐标。将经度(longitude)、纬度(latitude)、位置名称(member)添加到指定的 key 中。
127.0.0.1:6379[2]> geoadd loc 13.36 38.11 shanghai 15.08 37.50 nanjing
(integer) 2
# 计算两个位置之间的距离 GEODIST key member1 member2 [m|km|ft|mi]
127.0.0.1:6379[2]> geodist loc shanghai nanjing 。
"165679.0071"
# 根据用户给定的经纬度坐标来获取指定范围内的地理位置集合。
127.0.0.1:6379[2]> georadius loc 15 37 100 km
1) "nanjing"
# geopos 用于从给定的 key 里返回所有指定名称(member)的位置(经度和纬度),不存在的返回 nil。
127.0.0.1:6379[2]> geopos loc shanghai xian
1) 1) "13.35999995470047"
2) "38.110000286715028"
2) (nil)
# GEORADIUS key longitude latitude radius m|km|ft|mi [WITHCOORD] [WITHDIST] [WITHHASH] [COUNT count] [ASC|DESC] [STORE key] [STOREDIST key]
# GEORADIUSBYMEMBER key member radius m|km|ft|mi [WITHCOORD] [WITHDIST] [WITHHASH] [COUNT count] [ASC|DESC] [STORE key] [STOREDIST key]
7.HyperLogLog 基数统计
使用场景:
- 访问量巨大的基数统计,存在一定误差,占用内存少,稳定占用 12k 左右内存,可以统计 2^64 个元素
什么是基数?
比如数据集{1,3,5,7,5,7,8},那么这个数据集的基数集为{1,3,5,7,8}, 基数(不重复元素)为5。基数估计就是在误差可接受的范围内,快速计算基数。
127.0.0.1:6379[2]> pfadd mykey 1 2 3 1 4 # 添加元素
(integer) 1
127.0.0.1:6379[2]> pfcount mykey # 返回基数
(integer) 4
# PFMERGE 将多个 HyperLogLog 合并为一个 HyperLogLog , 合并后的 HyperLogLog 的基数接近于所有输入 HyperLogLog 的并集基数。
pfmerge destkey key1 key2 [...keyn]
8.BitMap 位图
使用场景:
- 用户签到(根据日期 offset = (今天是一年中的第几天) % (今年的天数),key = 年份:用户id。)
- 统计活跃用户(用户登陆情况,使用日期作为 key,然后用户 id 为 offset,如果当日活跃过就设置为1)
- 统计用户是否在线(只需要一个 key,然后用户 id 为 offset,如果在线就设置为 1,不在线就设置为 0。)
- 实现布隆过滤器
总结
懂你的人,会明白你的情绪起伏;不懂你的人,看不出你的喜怒哀乐;喜欢你的人,会感动你的真心真意;不喜欢你的人,你付出再多也是毫不在意。