likes
comments
collection
share

Redis数据类型-字符串详解

作者站长头像
站长
· 阅读数 21

首先,字符串是Redis最基础的数据结构,键都是字符串类型的,而其他四种类型的数据结构都是在字符串的基础上构建的。

字符串类型的值可以是字符串数字二进制.但是,值最大只能是512MB

下边我们从命令,编码,使用场景分别聊聊。

1 命令

1.1 常用命令

1.1.1 设置值

redis设置值,那么是个小可爱都知道我们可以通过命令set key value进行设置值,返回ok表示设置成功

127.0.0.1:6379> set name luke
OK

同时我们也可以加参数,加功能

  • ex seconds 设置秒级的过期时间
  • px milliseconds 设置毫秒级的过期时间
  • nx 键不存在的时候,才可以设置成功
  • xx 键存在的时候,才能设置成功

举个栗子: 设置key并且过期时间为10秒

127.0.0.1:6379> setex user 10 luke
OK

下来看看setnx, set xx 的区别吧

setnx

上边提到了setnx是不存在才可以设置成功,我们把库里的key全部清掉,然后将同样的命令执行两遍可以看到第一次由于key为name的不存在设置成功了,返回1,第二次设置的时候,由于第一次name已经存在了,就设置失败了。

127.0.0.1:6379> setnx name luke
(integer) 1
127.0.0.1:6379> setnx name luke
(integer) 0

set xx

set xx则是当key存在的时候才能设置成功。那么: 当设置redis里没有的值user的时候,返回nil。表示不存在 当设置我们上边已经存入的key name的时候,则返回ok表示成功

127.0.0.1:6379> set user luke xx
(nil)
127.0.0.1:6379> set name yan xx
OK

敲重点,setnx可以用来实现分布式锁呦,当多个线程设置同一个key的时候,由于redis的单线程模型,只有第一个设置的可以成功,其余的将设置失败。

1.1.2 获取值

get key可以获取到指定key的值 当获取的key存在的时候,返回该key对应的value值,当key不存在的时候,则返回nil。

127.0.0.1:6379> get name
"yan"
127.0.0.1:6379> get user
(nil)

1.1.3 批量设置值

通过mset key value key value ...可以批量的设置值

127.0.0.1:6379> mset a 1 b 2 c 3
OK

1.1.4 批量获取值

批量获取值的命令就是mget key key ...

127.0.0.1:6379> mget a b c
1) "1"
2) "2"
3) "3"
127.0.0.1:6379> mget a b c d
1) "1"
2) "2"
3) "3"
4) (nil)

当mget后边有不存在的key的时候,将对应的位置将显示nil

mget和mset命令的优点在于一次网络IO,批量获取或者设置数据。有助于提高业务处理效率,

1.1.5 计数

这个就比较常用了,我们平时系统中的点赞,喜欢,浏览量等数据,用redis的计数功能实现是非常容易的。

incr key用于对值进行自增操作,有三种返回结果。

  • value值不是整数,将报错
127.0.0.1:6379> set num a
OK
127.0.0.1:6379> incr num
(error) ERR value is not an integer or out of range
  • value值是整数,自增返回
127.0.0.1:6379> set sum 1
OK
127.0.0.1:6379> incr sum
(integer) 2
  • value值不存在,将按照值为0自增,返回1
127.0.0.1:6379> exists number
(integer) 0
127.0.0.1:6379> incr number
(integer) 1
127.0.0.1:6379> get number
"1"

1.2 不常用命令

1.2.1 追加值

append key value命令可以向字符串尾部追加值:

127.0.0.1:6379> set test1 luke
OK
127.0.0.1:6379> append test1 lala
(integer) 8
127.0.0.1:6379> get test1
"lukelala"

1.2.2 字符串长度

strlen key可以返回当前字符串的长度

127.0.0.1:6379> set name luke
OK
127.0.0.1:6379> strlen name
(integer) 4

对于中文来说,一个汉字是3个字节

1.2.3 设置新值并返回原值

getset key value可以设置值并返回key原本的值,若是原本key不存在,则会返回nil。

127.0.0.1:6379> getset user luke
(nil)
127.0.0.1:6379> getset user demi
"luke"

1.2.4 设置指定位置的字符

当我们需要修改指定位置的字符的时候,可以使用setrange key offset value

127.0.0.1:6379> get name
"luke"
127.0.0.1:6379> setrange name 0 a
(integer) 4
127.0.0.1:6379> get name
"auke"

1.2.5 获取部分字符串

getrange key start end可以获取指定位置的字符串,从0开始依次排序

127.0.0.1:6379> get name
"auke"
127.0.0.1:6379> getrange name 0 1
"au"

2 内部编码

字符串类型的内部编码有三种

  • int 8个字节的长整型
  • embstr 小于等于39个字节的字符串
  • raw 大于39个字节的字符串

2.1 整数

整数当然就是数字了

127.0.0.1:6379> set key 123456
OK
127.0.0.1:6379> object encoding key
"int"

2.2 短字符串

127.0.0.1:6379> object encoding key
"embstr"

2.3 长字符串

127.0.0.1:6379> set keu asdfghjklqwertyuioipzxcvbnmqwertyuiopasdfghjkl
OK
127.0.0.1:6379> object encoding keu
"raw"

这个很简单,就不做过多的赘述,之后我们会说到字符串类型的内存优化技巧,敬请期待

3 典型使用场景

3.1 缓存

缓存是redis最常见的使用场景,一般情况下,redis作为缓存层,mysql作为存储层,先从缓存中获取数据,若是失败,则会去数据库获取数据并向缓存中存储一份。这样的话不仅加快了读写的效率,也缓解了数据库的压力。

3.2 计数

redis一般也会作为基本的计数工具,比如我们商城项目中的浏览量,收藏量,这些每次加一的数据我们一般用redis的计数功能。

3.3 共享session

共享session是我们做单点登录的时候,当第一次登录的时候将session存储到redis中,每个点登陆进来只需要读取session,就可以就确定用户与角色。这样就避免了重复登录的操作。

3.4 限流

有时候,为了防止服务被突然袭来的大流量冲垮,需要做限流,redis也可以做限流的操作。 比如为了限制发送短信验证码10分钟内只能发5次。 设计思路可以是这样: 先setnx一个value为0,过期时间为600秒的的key,然后每访问一次就进行incr自增,当自增到5的时候,就拒绝访问。当600秒过了就又可以setnx一个0来继续自增。

又或者进行限速,比如一个服务1秒钟只接受一个请求,那么就setnx一个key,过期时间为1秒,当其他线程设置值的时候便会失败,只能等之前的key过期然后继续。