一、Redis的简介
1.1 Redis基本信息
- Redis是当前互联网世界最流行的NoSQL(Not Only SQL)数据库,NoSQL在互联网系统中的作用很大,因为它可以在很大程度上提高互联网的性能。
- Redis具备一定持久层的功能,也可以作为一种缓存工具,对于NoSQL数据库而言,作为持久层,它存储的数据是半结构化的,这就意味着计算机在读入内存中有更少的规则,读入速度更快。
- 对于那些结构化,多范式的数据库系统而言,它更具性能优势,作为缓存,它可以支持大数据存入内存,只要命中率高,他就可以快速响应,因为在内存中的数据读写数据库读写磁盘的速度快几十甚至到上百倍。
1.2 Redis的优点
- 因为数据库系统有更好的规范性和数据完整性,功能更加强大,作为持久层更为完善,安全性能也更高,而NoSQL结构松散,不完整,功能有限,但是作为缓存工具,它的高性能,高响应等功能,使它成为一个很重要的工具。
- Redis响应非常快:
- 每秒可以执行大约110000个写入操作,或者81000个读操作,其速度远超数据库,如果存入一些常用的数据,就能有效提高系统的性能。
- 支持6种数据结构
- 他们是字符串,哈希结构,列表,集合,可排序集合和基数。比如对于字符串可以存入一些java数据类型,哈希可以存储对象,列表可以存储List对象等,这使得在应用中很容易根据自己的需要选择存储的数据类型,方便开发。
- 操作都是原子性的
- 所有的Redis操作都是原子性的,从而确保当两个客户同时访问Redis服务器时,得到的是更新后的值,在需要高并发的场合可以考虑使用Redis的事务,处理一些需要的业务。
- MultiUtility工具
- Redis可以在如缓存,消息队列中使用(Redis支持“发布+订阅”的消息模式),在应用程序如Web应用程序会话,网站页面点击数等任何短暂的数据中使用。
- NOSQL从数据库中读取数据进行缓存,就可以从内存中读取数据了,而不像数据库一样读磁盘,现实是读操作远比写操作要多的多,所以缓存很多常用的数据,提高其命中率有助于整体性能的提高,并且能减缓数据库的压力,对互联网系统架构是十分有利的。
- 另一方面,他也可以满足互联网高并发需要告诉处理数据的场合,比如抢红包,商品秒杀等场景,这些场合需要告诉处理,并保证并发数据安全和一致性。
- Redis都是单线程的,避免线程切换来校以及线程竞争的为题
- 支持持久化,Redis总共支持RDB和AOF两种出久华方案,持久化有效避免了数据丢失的问题;
- 支持事务,
- 支持主存复制,主节点将数据通过步给从节点,可以进行读写分离;
1.3 Redis的8个应用场景
- 缓存-热数据
- 热点数据(经常会被查询,但是不经常被修改或者删除的数据),首选是使用Redis缓存,毕竟强大到冒泡的QPS和极强的稳定性不是所有类型工具都有的,而且相比于memcached还提供了丰富的数据类型可以使用,另外内存中的数据提供了AOF和RDB等持久化机制可以选择。
- 计数器
- 注入统计点击数等应用,由于是单线程,可以避免并发问题,保证不会出错,而且100%毫秒级性能。
- 位操作(大数据处理)
- 用于数据量上亿的场景下,例如几亿用户系统签到,去重登陆次数统计,某用户是否在线状态等等;
- 分布式锁与单线程机制
- 验证前端的重复请求(可以自由扩展类似情况),可以通过Redis进行过滤,每次请求将request ip、参数、接口等hash作为key存储在Redis,设置多长时间的有限期,然后下次请求过来的时候现在Redis中检索有没有这个key,进而验证是不是一定时间内过来的重复提交秒杀系统,基于Redis是单线程特征,防止出现数据库爆破全局增量ID生成,类似秒杀。
- 最新列表
- 排行榜
- 使用场景
- 数据的高并发的读写;
- 海量数据的续写;
- 对扩展性要求高的数据;
1.4 Redis是单线程
- Redis是基于内存操作的,CPU不是Redis的性能瓶颈,Redis的性能问题来自于机器内存和网络宽带,既然可以使用单线程来实现,那么就使用单线程。
- 单线程的好处
- 避免了过多的上下文的切换的开销
- 避免同步机制的开销,如果是多线程模型,需要考虑数据同步的问题,必然引起同步机制,如锁机制,增加程序的复杂度;
- 实现简单,方便维护
二、Redis的基本操作
- Redis中默认有16个数据库(从0到15),默认使用第0个数据库,可以通过select进行切换。
1 select:
- 切换数据库 ,返回值为OK,即切换数据库成功;
2 dbsize:
- 查看当前数据库中数据的个数,set方法是往数据库中写入数据(返回为OK则表示写入成功)
3 keys
- 查看所有的key,
4 flushdb
- 清空当前数据库,
5 flushall
四、Redis基于基本数据类型的命令
String:字符串
- String类型是Redis中的基本类型,一个key对应一个value;
- String类型的值可以使字符串,数字或者是二进制的数据,最大不超过512M;
1 set
- 添加数据
2 get
- 通过key获取值
3 exists
- 判断key是否存在,存在返回1,不存在返回0;
4 append
- 追加字符串,如果key存在,就追加,如果key不存在,相当于set;
5 strlen
- 获取字符串的长度
6 incr & decr
- 对value进行自增加1(自减减1)操作;
- 注意,这里只能对基本数据类型进行操作,字符串会报错
- 如果key不存在,那么value的值先会被初始化为0,然后再进行自增或自减操作;
7 incrby & decrby
- 设置加减的步长,也就是以多少步长进行自增和自减;
8 setrange & getrange
- 从指定位置开始替换字符串中的值,返回值表示value的长度;
9 setex & ttl
- 设置过期时间,查看剩余时间
10 setnx
- 如果key不存在则设置,否则失败不设置,当key存在的时候,就返回1,不存在就返回0;可以基于setnx实现分布式锁。
11 mset & mget
- 批量的插入数据和批量的获取数据
12 getset
- 先获取值,然后再设置值;如果成功,则返回原来的值,否则返回空(nil);
Hash:哈希
- hash类型适合存储对象,hash的命令都是以h开头的
1 hset & hget
- 设置数据和获取数据
2 hmset & hmget
- 批量化的设置数据和获取数据;
3 hgetall
- 获取key中的所有的value值;
4 hdel
- 删除指定的filed的hash键值对
5 hlen
- 获取hash中键值对的个数;
6 hexists
- 判断hash中字段是否存在,不存在的时候返回0,存在的时候返回1;
7 hkeys & kvals
- 获取hash中的所有的filed和获取hash中的所有的value;
8 hincrby
- 给定hash中字段的值加上一定步长,
9 hsetnx
- 如果存在,则添加成功,返回1;否则,添加失败返回0
List :列表
- 列表是简单的字符串列表,按照插入的顺序进行排序,数据是可以重复的,可以在头部和尾部进行插入和删除;
- 类似于java中的LinkedList集合
- 可以使用该类型的实现栈,队列等数据结构
1 lpush & rpush & lrange
- 从列表的左边插入和从列表的右边进行插入
- 查看从list中获取指定范围内的数据的个数
2 lpop & rpop
- 从左边或者从右边删除数据
3 lindex
- 获取指定下标的值
4 llen
- 获取list中元素的个数
5 lrem
- 删除list中的元素
6 ltrim
- 截取列表中的值
7 rpoplpush
- 移除列表中的最后一个元素,将它添加到另外一个list中
8 lset
- 根据下标替换列表中的值
9 linsert
- 在列表中插入值,在指定元素前或者后插入数据, 如果指定的数据重复,只找到第一个出现的元素在其前后进行插入即可;
- 使用列表完成数据结构
- 实现栈(先进后出):lpush+lpop
- 实现队列(先进先出):lpush+ rpop
- 有限集合:lpush+ ltrim
set:集合
- Redis中的set是String类型的无序集合,数据是无序的,并且属性元素是唯一的,意味着不能出现重复元素
- 命令的开头以s开头
1 sadd
- 给set中添加元素,当集合中元素不存在的时候,添加成功返回集合中的元素个数,如果添加的元素重复,就会返回0.
2 smembers
- 获取set中的所有的值
3 sismember
- 判断某个元素是否在set中,如果在set中,就返回1,不存在就返回0;
4 scard
- 获取set中的元素的个数
5 srem
- 删除set中的元素
6 srandmember
- 从set中随机获取值
7 spop
- 随机删除指定元素格式
8 smove
- 将指定元素从一个set中移动到另一个set中
9 sinter & sunion & sdiff
- 分别求交集,并集,补集;
SortSet:有序集合
- sortSet和set类似,集合中数据元素不能重复,
- 有序集合可以实现元素排序,给定内个元素设置一个分数,作为排序的依据
- 有序集合中的元素不能重复,但是分数是可以重复的。
- 有序卷积核一般以Z开头
1 zadd
- 添加元素
2 zrangebyscore
- 按照zset从小到大进行排序
3 zrem
- 删除zset中的元素
4 zcard
- 查看zset中元素的个数
5 zcount
- 更具score的值统计在给定区间的元素个数
- 应用场景,如排行榜,按照时间序列的新闻等等;
五、应用场景
1 缓存
- 一般使用String类型
- 缓存热点数据,对象缓存,页面缓存,降低数据库压力;
2 数据共享
- Redis相对于引用数据是独立服务,可以在多个应用之间共享;
3 分布式锁
- String类型的setnx只有在不存在的情况下才能添加成功
4 全局ID
- 给定一个全局发号器,依次给定一段号,每个服务器使用完再来申请,incrby通过步长设置来获取,利用Redis操作的原子性。
5 计数器
- incr方法:如文章阅读量,微博的点赞量
6 限流
- 一般通过访问的ip加其他信息作为一种key,访问依次加1,超过设定的阈值直接返回
7 Top问题
微博热搜按照访问量zset处理
8 消息队列
- list提供了两端操作的方法,rpush,lpush,rpop,lpop等操作
- 通过操作可以实现队列栈等结构
9 用户关注,推荐模型
- sdiff():获取差集,推荐(好友推荐,粉丝推荐,关注话题推荐)
- sinter():获取交集,(共同好友,共同话题)
- sunion():获取并集(所有好友,所有话题)
10 排行榜
- 新闻排行榜,微博热搜
六、Redis特殊类型
- geospatial地理空间
- 主要用于存储地理位置的信息,并对存储的信息进行操作;
- 适用场景如:定位,附近的人
1 geoadd & geopos
2 geodist
- 返回两个给定位置之间的距离
3 georadius
- 以给定的经纬度为中心,找到一个半径内的元素
4 georadiusbymember
- 以一个成员为中心,查找指定范围内的元素
|