Redis原理浅析(一):Redis基本数据类型、事务以及排序
什么是Redis
redis是一款优秀的nosql(非关系型),key-vlaue,内存级别的数据库!redis是单线程,操作是安全的!
- key-value:字典数据结构,“key”是键名,“value”是键值,在字典中我们可以获取或设置键名对应的键值,也可以删除一个键。
- 内存存储:redis数据库中所有的数据都存储在内存中。由于内存的读写速度远快于硬盘,因此redis在性能上对比其他基于硬盘存储的数据库有非常明显的优势。
- 持久化:redis提供了对持久化的支持,即可以将内存的数据异步写入到硬盘中,同时不影响继续提供服务。
Redis的数据类型
String :
String是redis最基本的类型,一个key对应一个value。String类型是二进制安全的。意思是redis的string可以包含任何数据。比如图片或者序列化的对象。String类型是Redis最基本的数据类型,一个键最大能存储512MB。
常用命令:
- get、获取存储在指定键中的值
- set、设置存储在指定键中的值
- del、删除存储在指定键中的值(这个命令可以用于所有的类型)
(1)设置一个键,获得该键值,并判断一个键是否存在
(2)删除键
(3)增和减
(4)向尾部追加值
(5)获取字符串长度
(6)同时获得/设置多个键值
使用场景:利用incr生成id,decr减库存, 缓存–过期时间设置,模拟session
List:
Redis list是简单的字符串列表,按照插入顺序排序。你可以添加一个元素到列表的头部(左边)或者尾部(右边)。
常用命令:
- rpush:将给定值推入列表的右端
- lrange:获取列表在指定范围上的所有值
- lindex:获取列表在指定范围上的单个元素
(1)向列表添加元素、弹出元素、获取表中元素个数、获得列表片段
(2)获得/设置指定索引的元素值
(3)向列表中插入元素
使用场景: 多任务调度队列
Set
Redis的Set是string类型的无序集合。集合是通过哈希表实现的,所以添加,删除,查找的复杂度都是O(1)。
常用命令:
- sadd:将给定元素添加到集合
- smembers:返回集合包含的所有元素
- sismember:检查指定元素是否存在于集合中
(1)增加或删除元素以及获得集合中所有元素:
(2)判断元素是否存在于集合中:
(3)集合的运算差:sdiff,交:sinter,并:sunion
使用场景: 微博关注数
hash
Redis hash 是一个键值(key=>value)对集合。Redis hash是一个string类型的field和value的映射表,hash特别适合用于存储对象。
常用命令:
- hset:在散列里面关联起指定的键值对
- hget:获取指定散列键的值
- hgetall:获取散列表包含的所有键值对
- hdel:如果给定键存在于散列里面,那么移除这个键
(1)为键值car设置price、name、model等“属性”
(2)判断model字段是否存在,不存在的话添加该字段,最后删除
使用场景:购物车
zset
Redis zset 和 set 一样也是string类型元素的集合,且不允许重复的成员。不同的是每个元素都会关联一个double类型的分数。redis正是通过分数来为集合中的成员进行从小到大的排序。zset的成员是唯一的,但分数(score)却可以重复。
常用命令:
- zadd、将一个带有给定分值的成员添加到有序集合里面
- zrange、根据元素在有序排列中所处的位置,从有序集合里面获取多个元素
- zrangebyscore、获取有序集合在给定分值范围内的所有元素
- zrem、如果指定成员存在于有序集合中,那么移除这个成员
(1)增加元素、获得元素分数、获得排名在某个范围的元素列表、获得制定分数范围的元素
使用场景:排行榜
事务
Redis 事务可以一次执行多个命令, 并且带有以下三个重要的保证:
①批量操作在发送 EXEC 命令前被放入队列缓存。
②收到 EXEC 命令后进入事务执行,事务中任意命令执行失败,其余的命令依然被执行。
③在事务执行过程,其他客户端提交的命令请求不会插入到事务执行命令序列中。
一个事务从开始到执行会经历以下三个阶段:
①开始事务。 ②命令入队。 ③执行事务。
MULTI开启事务,EXEC结束事务
*如转账过程中,A给B汇款,首先从A的账户中将钱划走,然后向B的账户增加相应的的金额。这两步必须属于同一事务,要么全执行,要么全不执行
错误处理:
(1)语法错误:指令不存在或者参数的个数不对;执行EXEC后Redis直接返回错误,正确的语法也不会执行。
(2)运行错误:命令执行时出现错误,如散列类型的命令操作集合类型的键,这种错误在实际执行之前是不会被发现的,所以其他命令会继续执行。
Watch命令:
监控一个或多个键,一旦有一个被修改(或删除),之后事务就不会执行。
控制键的存活时间
①Expire key seconds 单位秒,多少秒后键自动删除
②Ttl key 返回键的剩余时间
③Persist key取消键的时间设置 成功则返回1
如限时活动、缓存或验证码,实现访问频率的限制 ;实现缓存机制。
排序
sort命令可以对列表类型、集合类型和有序类型键进行排序,并且可以完成与关系数据库中的连接查询相似的任务:
Sort key (alpha:字母;desc:降序;limit[start,end];by参数)
①By:通过使用 BY 选项,可以让 uid 按其他键的元素来排序。
②Get:使用 GET 选项, 可以根据排序的结果来取出相应的键值。
③Store:选项指定一个 key 参数,可以将排序结果保存到给定的键上。
如果被指定的 key 已存在,那么原有的值将被排序结果覆盖。
构造如图表结构:
(1)Sort key1 by key2 将key1按照key2的大小进行排序
注意:user_level_* 是一个占位符, 它先取出 uid 中的值, 然后再用这个值来查找相应的键。
比如在对 uid 列表进行排序时, 程序就会先取出 uid 的值 1 、 2 、 3 、 4 , 然后使用 user_level_1 、 user_level_2 、 user_level_3 和 user_level_4 的值作为排序 uid 的权重。
(2)get:sort key1 get key2 按照key1大小进行排序,将key2结果显示出来
(3)sort、by、get结合使用:可以同时使用多个 GET 选项, 获取多个外部键的值。
(4)GET 有一个额外的参数规则,那就是 —— 可以用 # 获取被排序键的值。
以下代码就将 uid 的值、及其相应的 user_level_* 和 user_name_* 都返回为结果: