1、Redis基本命令
# 切换数据库
SELECT index
# 当前数据库有的数据量
DBSIZE
# 清空当前数据库内容
FLUSHDB
# 清空所有数据库内容
FLUSHALL
1.1 key
# 删除指定key(一个或多个)
DEL key [key ...]
# 序列化指定key的值
DUMP key
# 查询key是否存在
EXISTS key
# 设置一个key的过期时间(s)
EXPIRE key seconds
# 获取key的有效时间(s)(-1,永久有效;-2,无效,没有该key)
TTL key
# 移除key的过期时间
PERSIST key
# 查找所有匹配给定的模式的键(通配符: *: 代表所有; ?: 代表一个字符)
KEYS pattern
# 返回一个随机的key
RANDOMKEY
# 将一个key重命名
RENAME key newkey
# 重命名一个key,新的key必须是一个不存在的key
RENAMENX key newkey
# 移动一个key到另一个数据库
MOVE key db
EXPIRE key命令,应用场景
- 限时的优惠活动信息
- 手机验证码
- 限制网站访客访问频率
1.2 key命名规范
redis中单个key存入512M大小。
NOSQL中数据与数据间是没有任何关联的,通过命名来解决。
- key不要太长,尽量不要超过1024字节,这不仅消耗内存,而且降低查询效率;
- key也不要太短,太短的话,可读性降低;
- 在一个项目中,key最好使用统一的命名模式,例如:user:id :name、user&id&name;
- key的名称区分大小写,命令不区分大小写。
2、Redis 数据类型
2.1 String
2.1.1 简介:
string 是 redis最基本的数据类型,一个key对应一个value,一个键最大能存储512MB;
string 类型是二进制安全的,意思是 redis 的string 可以包含任何数据,比如:jpg图片或序列化的对象。
二进制安全是指,在传输数据时,保证二进制数据的信息安全,也就是不被篡改、破译等,如果被攻击,能够及时检测出。
二进制安全特点:
- 编码、解码发生在客户端完成,执行效率高;
- 不需要频繁的编码解码,不会出现乱码
2.1.2 string命令
# 赋值语法
# 设置给定 key的值,如果key已经存在值,覆盖旧值,且无视类型
SET key value
# key不存在时,为key赋值;key存在,命令失效
SETNX key value // 重要,分布式锁问题
# 为多个key-value赋值
MSET key value [key value...]
# 追加一个值到key上,返回字符串长度
APPEND key value
# 取值语法
# 返回 key 的value
GET key
# 获取存储在key上的值的一个字符串,start - end表示取值范围(0-x)
GETRANGE key start end
# 设置一个key的值,并获取设置前的值(应用场景广泛)
GETSET key value
# 获取指定key值的长度
STRLEN key
# 返回位的值存储在关键的字符串值的偏移量
GETBIT key offset
# 删除语法
# 删除指定key,如果存在,返回数字类型(删除的个数)
DEL key
# 自增、自减,并返回结果数
# 将key存储的值自增加一,如果key不存在,那么key的值会先初始为0,再执行incr操作
INCR key
# 将key存储的值自增自定义的数,如果key不存在,那么key的值会先初始为0,在执行incrby操作
INCRBY key increment
# 自减一
DECR key
# 自减自定义的值
DECRBY key increment
2.1.3 应用场景
- String 通常用于保存单个字符串或JSON字符串数据;
- 因String是二进制安全的,所以完全可以把一个图片文件的内容作为字符串来存储;
- 计数器,(常规key-value 缓存应用,常规技术:阅读数、评论数)
**INCR 等指令本身就是具有原子操作的特性,**所以我们完全可以利用 INCR、INCRBY、DECR、DECRBY等指令来实现原子计数的效果。
不少网站都利用redis的这个特性来实现业务上的统计计数需求。
2.2 hash类型
2.2.1 简介
-
hash 是一个string类型的 field 和 value 的映射表,hash特别适合用与存储对象。
-
redis 中可以存储 2^32 - 1 键值对(40多亿),可以看做具有KEY和VALUE的map容器,该类型非常适合于存储值对象的信息,如:uname,ugender,uage。该类型的数据仅占用很少的磁盘空间(相比于JSON)。
2.2.2 hash命令
# 赋值语法
# 为指定的key,设定key/value.相当于 key:对象名 field:属性名 value:属性值
HSET key field value
# 同时将多个 field-value(域-值)对设置到哈希表key中
HMSET key field value [field value]...
# 取值语法
# 取出 key 的field的值
HGET key field
# 取出 key 中多个field的值
HMGET key field [field...]
# 获取 key 的所有 field 和 value
HGETALL key
# 获取key中所有field
HKEYS key
# 获取 key 中field的数量
HLEN key
# 删除语法
# 删除key中一个或多个field,当key的所有field的值都删除完了,redis会删除这个key
HDEL key field [field...]
# 其他语法
# 只有key不存在时,设置字段的值
HSETNX key field value
# 为哈希表key中的指定字段的整数值加上增量increment
HINCRBY key field increment
# 为哈希表key中的指定字段的浮点数值加上增量increment
HINCRBYFLOAT key field increment
# 查看哈希表key中,指定的field是否存在
HEXISTS key field
2.2.3 应用场景
-
常用于存储一个对象;
-
为什么不用string存储一个对象?
-
hash是最接近关系型数据库结构的数据类型,可以将数据库一条记录或程序中一个对象转换成hashmap存放到redis中;
-
用string存储对象的两种方式:
- 第一种,将用户id作为查找的key,把其他信息封装成一个对象以序列化的方式存储(json)。缺点:增加了序列化/反序列化的开销,并且在需要修改其中一项信息中,需要把整个对象取出,并且修改操作需要对并发进行保护,引入CAS等复杂问题;
例:key:id,value:{json串}
- 第二种,这个用户信息对象有多少成员就存成多少个key-vale对,用户ID+对应属性的名称作为唯一表示来取得对应属性的值。(例:set user:id 1;set user:name xiaojian;set user:gender “男” )虽然省去了序列化开销和并发问题,但是用户ID为重复存储,如果存在大量这样的数据,内存浪费巨大。
例: key:user:id 1 user:name xiaojian user:age 22
-
2.3 List类型
2.3.1 简介
简单的字符串列表,按照插入顺序排序。可以添加一个元素到列表的头部(左边)或尾部(右边)
List 存入的元素的结构就像栈堆,先进后出
类似于 Java 的 LinkedList
127.0.0.1:6379> lpush list2 1
(integer) 1
127.0.0.1:6379> lpush list2 2
(integer) 2
127.0.0.1:6379> lpush list2 3
(integer) 3
127.0.0.1:6379> lpush list2 3
(integer) 4
127.0.0.1:6379> lrange list2 0 -1
1) "3"
2) "3"
3) "2"
4) "1"
2.3.2 List命令
# 赋值语法
# 从列表左边存入一个或多个元素
LPUSH key value[value...]
# 当列表存在时,从列表左边存入一个(列表不存在,无法存入)
LPUSHX key value
# 从列表右边存入一个或多个元素
RPUSH key value[value...]
# 当列表存在时,从列表右边存入一个(列表不存在,无法存入)
RPUSHX key value
# 在列表中的另一个元素之前或之后插入一个元素
LINSERT key BEFORE|AFTER pivot value
如:linsert list1 BEFORE "c" "b" # 在元素 "c" 之前插入 "b"
# 根据索引,设置列表里面一个元素的值
LSET key index value
# 取值语法
# 通过其索引获取一个元素
LINDEX key index
# 从列表获取指定范围内的元素,start和stop偏移量为 -1 指最后一个元素,-2指倒数第二个,一次类推
LRANGE key start stop
# 获取列表长度
LLEN key
# 截取指定范围的数据,列表中的数据改变成截取的数据
LTRIM key start stop
# 删除语法
# 从列表最左边移除一个元素,并返回这个元素
LPOP key
# 从列表最右边移除一个元素,并返回这个元素
RPOP key
# 从存于 key 的列表里移除前 count 次出现的值为 value 的元素。
# count为正数时,移除前count个;为负数时,移除后count个;为0,移除所有value
LREM key count value
2.3.3 应用场景
-
对数据量显示、关注列表、粉丝列表、留言评价等…分页、热点新闻(Top5)等;
利用 LRANGE 还可以很方便的实现分页的功能;在博客系统中,每篇博文的评论也可以存入一个单独的list中。
-
任务队列
list通常用来实现一个消息队列,而且可以确保先后顺序,不必像MySQL那样还需要通过 ORDER BY来进行排序
#任务队列介绍(生产者和消费者模式): # 在处理web客户端发送的命令请求时,某些操作的执行时间可能会比我们预期的更长一些,通过将待执行任务的相关信息放入队 列里面,并在之后对队列进行处理,用户可以推迟执行那些需要一段时间才能完成的操作,这种将工作交给任务处理器来执行的做法 被称为任务队列(task queue)。 RPOPLPUSH source destination # 一处列表的最后一个元素,并将该元素添加到另一个列表并返回(对同一个list使用,把最后一个元素,调到首个)
2.4 Set 类型
2.4.1 简介
不允许存在重复元素的集合,无序
Redis集合时通过哈希表实现的,所以添加,删除,查找的复杂度都是 O(1),
set是通过 hashtable
实现的,
集合中的最大成员数为 232 - 1(4294967295,每个集合可存储40多亿个成员)
类似 Java 中的成员 Hashtable
集合
2.4.2 Set 命令
# 赋值语法
# 添加一个或多个元素
SADD key member [member...]
# 取值语法
# 获取集合中所有元素
SMEMBERS key
# 获取集合长度
SCARD key
# 判断 member 元素是否是集合 key 的成员(开发中:验证是否存在判断)
SISMEMBER key member
# 返回集合中一个或多个随机数
SRANDMEMBER key [count]
# 差集语法:
SDIFF key1 [key2] : 返回给定 key1 集合与其他集合的差集
SDIFFSTORE destination key1 [key2] : 返回给定所有集合的差集并存储在 destination 中(destination是一个新建的key的名称)
# 交集语法:
SINTER key1 [key2] : 返回给定所有集合的交集(共有数据)
SINTERSTORE destination key1 [key2] : 返回给定所有集合的交集并存储在 destination 中(destination是一个新建的key的名称)
# 并集语法:
SUNION key1 [key2] : 返回所有给定集合的并集
SUNIONSTORE destination key1 [key2] : 返回给定所有集合的并集并存储在 destination
# 删除语法
# 删除一个或多个元素
SREM key member1 [member2]
# 移除并返回集合的一个随机元素
SPOP key [count]
# 将 member 元素从 source 集合移动到 destination 集合
SMOVE source destination member
2.4.3 应用场景
常应用于:对两个集合间的数据 [计算] 进行交集、并集、差集运算
- 利用集合操作,可以取不同兴趣圈子的交集,以非常方便的实现如共同关注、共同喜好、二度好友等功能。对上面的所有集合操作,你还可以使用不同的命令选择将结果返回给客户端还是存储到一个新的集合中。
- 利用唯一性,可以统计访问网站的所有独立 IP、存取当天(或某天)的活跃用户列表。
2.5 ZSet 类型
2.5.1 简介
有序集合(sorted set)
不允许重复元素,且元素有序
插入元素时都会关联一个double类型的分数(score),以分数从小到大排序
有序集合的成员是唯一的,但分数(score)却可以重复
(我们将在redis中的有序集合叫做zsets,这是因为在 redis 中,有序集合相关的操作指令都是以z开头的)
2.5.2 ZSet 命令
# 赋值语法
ZADD key score member [score member...]
# 取值语法
# 获取有序集合的成员数
ZACARD key
# 计算在有序集合中指定区间分数的成员数
ZCOUNT key min max
# 返回有序集合中指定成员的索引
ZRANK key member
# 通过索引区间返回有序集合中指定区间的成员(0,-1)
ZRANGE key start end [WITHSCORES]
# 通过分数返回有序集合指定区间内的成员
ZRANGBYSCORE key min max [WITHSCORES] [LIMIT]
# 返回有序集合指定区间内的成员,通过索引,分数从高到低
ZREVRANGE key start stop [WITHSCORES]
# 返回有序集合指定分数区间内的成员,通过索引,分数从高到低
ZREVRANGEBySCORE key max min [WITHSCORES]
# 删除语法
# 移除集合
DEL key
# 移除有序集合中的一个或多个成员
ZREM key member [member ...]
2.5.3 应用场景
常应用于:排行榜
销量排名,积分排名等
2.6 HyperLogLog
简介
Redis 在2.8.9 版本添加了 HyperLogLog 结构
Redis HyperLogLog 是用来做基数统计的算法,HyperLogLog 的优点是,在输入元素的数量或体积非常大时,计算基数所需的空间总是固定的,并且是很小的
在 Redis 里面,每个 HyperLogLog 键只需要花费 12 KB内存,就可以计算接近 2^64 个不同元素的基数。这和计算基数时,元素越多耗费内存就越多的集合形成鲜明对比。
但是,因为 HyperLogLog 只会根据输入元素来计算基数,而不会储存输入元素本身,所以 HyperLogLog 不能像集合那样,返回输入的各个元素。
什么是基数?
比如数据集{1,3,5,7,5,7,8},那么这个数据集的基数集为{1,3,5,7,8},基数(不重复元素)为5。
基数估计就是在误差可接受的范围内,快速计算基数.
2.6.1 常用命令
# 添加指定元素到 HyperLogLog 中
PFADD key element [element ...]
# 返回给定 HyperLogLog 的基数估算值
PFCOUNT key [key ...]
# 将多个 HyperLogLog 合并为一个 HyperLogLog
PFMERGE destkey sourcekey [sourcekey ...]
2.6.2 应用场景
基数不大,数据量不大就用不上,会有点大材小用浪费空间
有局限性,就是只能统计基数数量,而没有办法知道具体内容是什么
统计注册 IP 数
统计每日访问 IP 数
统计页面实时 UV 数
统计在线用户数
统计用户每天搜索不同词条的个数
统计真是文章阅读数