redis操作合集,赶紧学起来,玩命卷

164 阅读11分钟

1、基本使用命令

redis默认16个库,默认使用第0个库

1.1、输出所有key

keys *

1.2、设置 key和vale

set k1 luck
set k1 wqwq

1.3、获取k1 对应的value

get k1

1.4、判断key是否存在 返回1表示存在

exists k1
-- 返回0,表示key不存在
exists k11

1.5、查看key的类型

type k1

1.6、删除key,返回1表示删除成功

del k1

1.7、非阻塞删除key

unlink k1

1.8、设置key的过期时间,单位为秒

expire k1 1

1.9、查看key的剩余过期时间,-1表示永不过期,-2表示已经过期

ttl k1

1.10、切换数据库

select 15

1.11、查看当前数据库key的数据

dbsize

1.12、清空当前库

flushdb

1.13、通杀全部库

flushall

2、五大数据类型

2.1、Redis字符串类型String

String 类型是 Redis 最基本的数据类型,一个Redis中字符串 value 最大可以是 512M。

2.1.1、String类型命令

2.1.1.2、(strlen)获取字符串长度

strlen k1

2.1.1.3、(setnx)设置key和value,当key不存在时,才会设置成功,key存在时,不设置

setnx k1 dasd
setnx k3 das

2.1.1.4、(incr)设置数字值增1,只能对数字生效

incr k4

2.1.1.5、(decr)设置数字值减1,只能对数字生效

decr k4

2.1.1.6、(incrby)设置数字增加自定义步长

incrby k4 121

2.1.1.7、(decrby)设置数字减少自定义步长

decrby k4 121

2.1.1.8、(mset)同时设置一个或多个key,value

mset k5  5 k6 6

2.1.1.9、(mget)同时获取一个或多个key的value

mget k5 k6

2.1.1.10、(mset)同时设置同时设置一个或多个key,value,且必须保存每个key都不存在,才会成功

-- 当k5存在时,设置失败
msetnx k5 5 k7 7
msetnx k7 7 k8 8

2.1.1.11、(getrange)获取指定范围的内的字符串

getrange k1 0 3

2.1.1.12、(setrange)设置字符串某个位置上的值

setrange k1 3 qw

2.1.1.13、(setex)设置key和value同时设置过期时间

setex k1 10 er

2.1.1.14、(getset)设置新值的同时返回旧值

getset k1 yutyu

2.1.2、数据结构

采用预分配冗余空间的方式,来减少重新分配内存的开销。

image.png 如图中所示,内部为当前字符串实际分配的空间 capacity 一般要高于实际字符串长度len。当字符串长度小于 1M时,扩容都是加倍现有的空间,如果超过 1M,扩容时一次只会多扩 1M的空间。需要注意的是字符串最大长度为 512M。。

image.png

3、BitMap位图

3.1是什么

image.png

说明:用String类型作为底层数据结构实现的一种统计二值状态的数据类型,位图本质是数组,它是基于String数据类型的按位的操作。该数组由多个二进制位组成,每个二进制位都对应一个偏移量(我们称之为一个索引)。
Bitmap支持的最大位数是2^32位,它可以极大的节约存储空间,使用512M内存就可以存储多达42.9亿的字节信息(2的32次方 = 4294967296)

3.2 能干什么

可以解决:每日签到、上下班打卡、是否播放过电影等需求
好处:实现同样的需求,可以解决空间,降低频繁的数据库操作,缓解数据库压力

3.3基本命令

命令作用时间复杂度
setbit key offset val给指定key的值的第offset赋值valO(1)
getbit key offset获取指定key的第offset位O(1)
bitcount key start end返回指定key中[start,end]中为1的数量O(1)
setbit key offset val给指定key的值的第offset赋值valO(1)
bitop operation destkey key对不同的二进制存储数据进行位运算(AND、OR、NOT、XOR)O(n)

3.3.1 setbit

bitmap的下标从左边0位开始

-- setbit key offset val
-- 给指定key的值的第offset赋值val
-- 给第2位设置为1
setbit bitkey1 1 1
-- 给第8位设置为1
setbit bitkey1  7 1

get bitkey1

image.png 执行完setbit bitkey1 1 1,这时bitkey1的值如下: image.png

3.3.2 getbit

getbit bitkey1 0
结果为: 0
getbit bitkey1 1
结果为: 1

说明bitmap每位的默认值为0

3.3.3 strlen统计长度

setbit bitkey2 0 1

setbit bitkey2  7 1

strlen bitkey2

此时返回1 image.png

在第9位上设置为1
setbit bitkey2  8 1

strlen bitkey2

此时返回2 image.png 结论:返回的数字不是字符串长度而是占据几个字节,超过8位后自己按照8位一组一byte再扩容

3.3.3 bitcount统计1的数量

--统计为1的数量,模拟用户签到

setbit uid:123 0 1

setbit uid:123 6 1

setbit uid:123 16 1

bitcount uid:123

image.png

3.3.4 bitop位操作


位操作BITOP operation destkey key [key ...]:对多个键key执行位运算操作
(ANDORNOTXOR),并将结果保存到destkey中。

举一个使用bitop统计用户连续登录数量的例子:
(1)首先将用户存取hash中

hset user 1 uid:123
hset user 2 uid:1234

hgetall user

此时1和2这两个key则代表用户 image.png (2)记录2024年6月18日的签到信息

-- 使用上面名为user的hash的key作为bitmap中的位
-- 此时表示用户uid:123在2024年6月18日签到
setbit 20240618 1 1
-- 此时表示用户uid:1234在2024年6月18日签到
setbit 20240618 2 1

(3)记录2024年6月19日的签到信息

-- 此时表示用户uid:123在2024年6月19日签到
setbit 20240619 1 1

(4)求连续签到的用户数量 等于 取20240618和20240619的并集

-- 以下操作代表对20240618和20240619取并集位操作,将并集结果存放到res位图中
bitop and res 20240618 20240619
-- 统计res中为1的数量,就等于为连续签到的用户数量
bitcount res

image.png

3.4应用场景

记录用户全年的签到信息
按年去存储一个用户的签到情况,365 天需要 365/8≈ 46 Byte,1000W 用户量一年也只需要440MB 就足够了。 假如是亿级的系统,每天使用1个1亿位的Bitmap约占12MB的内存(10^8/8/1024/1024),10天的Bitmap的内存开销约为120MB,内存压力不算太高。 此外,在实际使用时,最好对Bitmap设置过期时间,让Redis自动删除不再需要的签到记录以节省内存开销。

4、基数统计(HyperLogLog)

4.1需求

统计网站的UV、统计文章的UV、统计用户搜索关键词数量

4.1.1什么是UV

Unique Visitor,独立访客,一般理解为客户端IP

4.2简介

Redis 在 2.8.9 版本添加了 HyperLogLog 结构。 Redis HyperLogLog 是用来做基数统计的算法,HyperLogLog 的优点是,在输入元素的数量或者体积非常非常大时,计算基数所需的空间总公是固定的,并且是很小的。在 Redis 里面,每个 HyperLogLog 键只需要花费 12 KB 内存,就可以计算接近 2^64 个不同元素的基 数。这和计算基数时,元素越多耗费内存就越多的集合形成鲜明对比。 但是,因为 HvperLogLog 只会根据输入元赛来计算基数,而不会储存输入元表本身,所以 HvoerLogLog 不能像集合那样,返回输入的各个元素。 HyperLogLog 是一种概率数据结构,主要用于估算基数(不重复元素的数量)的大小,特别适用于大数据集,能够在极小的内存空间内提供非常高的准确性。

4.3命令

命令作用
PFADD key element [element ...]向 HyperLogLog 数据结构中添加一个或多个元素
PFCOUNT key [key ...]统计HyperLogLogs 中不同元素的总数
PFMERGE destkey sourcekey [sourcekey ...]多个 HyperLogLog 合并(合并后不会丢失精度)到一个新的 HyperLogLog 数据结构中

4.3.1 PFADD添加元素

--向hykey中添加 元素
pfadd hykey 1 2 3 4 5 6 7 8 9 1 2 3
-- 向hykey2中添加 元素
pfadd hykey2 1 2 3

4.3.2 PFCOUNT统计不同元素个数

-- 统计hykey中 hykey2不同元素的总数
pfcount hykey 
-- 统计hykey中 hykey2不同元素的总数
pfcount hykey hykey2

两个命令的结果都是 9

4.3.3 PFMAGER 合并

将hykey和hykey2合并到newhykey中

pfmerge newhykey  hykey hykey2

5、地理空间(GEO)

5.1简介

移动互联网时代LBS应用越来越多,交友软件中附近的小姐姐、外卖软件中附近的美食店铺、高德地图附近的核酸检査点等等,那这种附近各种形形色色的XXX地址位置选择是如何实现的? 地球上的地理位置是使用二维的经纬度表示,经度范围(-180,180],纬度范围(-90,90],只要我们确定一个点的经纬度就可以名取得他在地球的位置。 例如滴滴打车,最直观的操作就是实时记录更新各个车的位置,然后当我们要找车时,在数据库中査找距离我们(坐标x0,y0)附近r公里范围内部的车辆, sql如下

select taxi from position where x0-r < x < x0+r and y0-r < y < y0+r

但是这样会有什么问题呢?

  1. 查询性能问题,如果并发高,数据量大这种查询是要搞垮数据库的
  2. 这个查询的是一个矩形访问,而不是以我为中心r公里为半径的圆形访问。
  3. 精准度的问题,我们知道地球不是平面坐标系,而是一个圆球,这种矩形计算在长距离计算时会有很大误差

怎么解决?
核心思想就是将球体转换为平面,区块转换为一点

image.png

主要分为三步

  1. 将三维的地球变为二维的坐标
  2. 在将二维的坐标转换为一维的点块
  3. 最后将一维的点块转换为二进制再通过base32编码

5.2 命令

命令作用描述
GEOADD key longitude latitude member [longitude latitude member ...]向指定的 Geo Set 中添加一个或多个地理位置元素,每个元素包含经度、纬度和成员标识符。
GEOPOS key member [member ...]获取一个或多个成员在 Geo Set 中的精确地理位置(经度和纬度)。
GEODIST key member1 member2 [unit]计算两个成员在地球表面上的大致距离。可选地,可以指定距离单位(如米、千米等)。
GEORADIUS key longitude latitude radius m以给定的经纬度为中心, 返回键包含的位置元素当中, 与中心的距离不超过给定最大距离的所有位置元素。
GEORADIUSBYMEMBER key member radius mkm

5.2.1 GEOADD添加经纬度

拾取坐标系统 (baidu.com)

-- 在city中添加天安门,故宫,长城的地理坐标
geoadd city 116.403963 39.915119 "天安门" 116.403414 39.924091 "故宫" 116.024067 40.362639 "长城"
type city

5.2.2 GEOPOS 获取经纬度

-- 获取 天安门 故宫的地理坐标
geopos city 天安门 故宫

5.2.3 GEODIST 获取两个点的距离

-- 获取天安门 故宫的距离,km是单位千米,默认单位是m米
geodist city 天安门 故宫 km

单位有:

  • m 米
  • km 千米

5.2.4 GEOROUND 获取附近的点

获取王府井附近十千米内的点

-- 116.417622,39.920672 王府井的经纬度
georadius city 116.417622 39.920672 10 km

image.png

  • WITHDIST:在返回位置元素的同时, 将位置元素与中心之间的距离也一并返回。 距离的单位和用户给定的范围单位保持一致。
-- 返回和中心的的距离
georadius city 116.417622 39.920672 10 km withdist

image.png

  • WITHCOORD:将位置元素的经度和维度也一并返回。
-- 返回点的经纬度
georadius city 116.417622 39.920672 10 km withcoord

image.png

  • WITHHASH:以 52位有符号整数的形式, 返回位置元素经过原始 geohash 编码的有序集合分值。 这个选项主要用于底层应用或者调试。实际中的作用并不大。
georadius city 116.417622 39.920672 10 km withhash

image.png

  • COUNT 限定返回的记录数。
-- 只返回一条结果,注意:会按照和中心的的距离降序排列后取值
georadius city 116.417622 39.920672 10 km withdist count 1

image.png

  • ASC 将结果按照与中心之间的距离升序排列
georadius city 116.417622 39.920672 10 km withdist asc

image.png

  • DESC 将结果按照与中心之间的距离降序排列(默认,除了使用count时)
georadius city 116.417622 39.920672 10 km withdist desc

image.png

5.2.5 georadiusbymember通过成员名获取附近的点

-- 获取天安门附近十千米内的点
georadiusbymember city 天安门 10 km withdist

image.png