redis简介
- redis:高性能键值对nosql数据库,以单线程方式处理请求(原子性操作),基于内存存取数据。解决海量用户,高并发情况下数据处理问题。
- 问题描述:关系型数据库在海量数据,高并发下数据处理的问题
- 1、性能瓶颈:磁盘IO性能低下。
- 2、扩展瓶颈:关系型数据库数据之间关系复杂,扩展性差,不便于大规模集群。
- 解决方案:
- 1、内存IO
- 2、去掉数据键的复杂性
- redis特性
- 1、数据间无联系
- 2、高性能、单线程(操作都是原子性,不必考虑并发带来的问题)
- 3、多数据类型支持
- string
- list
- hash
- set
- sorted_set
- 4、数据持久化RDB/AOF,防止数据灾难
- RDB:数据快照,当前数据保存到文件中。(默认)
- AOF:记录所有写命令到文件,再次开启数据库时执行一遍写命令。
- redis应用
- 为热点数据加速查询(主要场景),如热点商品、热点新闻、热点资讯、推广类等高访问量信息等
- 任务队列,如秒杀、抢购、购票排队等
- 即时信息查询,如各位排行榜、各类网站访问统计、公交到站信息、在线人数信息(聊天室、网站)、设
备信号等 - 时效性信息控制,如验证码控制、投票控制等
- 分布式数据共享,如分布式集群架构中的 session 分离
- 消息队列
- 分布式锁
- 命令
- 帮助命令
- 单个命令help command
- 组命令help @string(组有string,list,hash…等)
- 清屏命令 clear
- 存取命令说明
- 存相关命令:不存在原信息,则创建, 存在则替换
- 取相关命令:不存在原信息,则返回nil
- set 和mset 使用场景
- 当数据量够大时,由于redis采用单线程处理,三个单独的set,效率不如一次mset三个数据,但是一次mset的数据也不能太大,否则单线程就阻塞在这里了,当数据量过大,可拆分成合适大小处理。
- 帮助命令
使用案例
- 数据库表id生成 incr
- redis所有操作都是原子性,incr自增操作生成数据库id
- 支持分表
- 支持数据库集群
- 投票(每4小时只能投一票) setex(秒) psetex(毫秒)
- 控制基于时效性的业务对象
- 投完票记录下投票者的id,存入redis中,设置过期时间为4小时,再次投票时判断redis中是否存在,存在(没过期)即不能再次投票。
- redis用于各种高热度结构性和非结构性数据
- 场景:明星的微博主页和我们的微博主页相比,他们的就是高热度的。此时他们主页的相关数据应存放的redis里,以便快速响应高并发的访问。
- 数据结构如下:
- user:id:fans
- user:id:focus
- 我们可以如上在redis中分开存放,也可以使用json同时存放,那种效果好视具体情况而定
- user:id:{fans:100,focus:10}
- redis中的数据大部分还是来自数据库,因此常用如下命名规则
- 表名:主键名:主键值:字段名
- user :id :100 :name
- hash结构适用于抢购,限购,限量优惠券,激活码等业务的数据存储。
- list应用场景
- 微博,微信点赞等,需要按照顺序显示关注的人,点赞的人,需要按照先后顺序呈现的数据 ,特别关注,最新发博,分组等。
- set应用场景
- 随机推荐类信息检索,例如热点歌单,热点新闻推荐,热点旅游线路,APP推荐,大V推荐。
- 使用set 的交集,并集,差集等处理共同好友显示,推荐好友,共同关注的公众号等数据的处理
- 数据不可重复,交叉数据类型处理
- 同类型数据去重,统计访问网站的不同用户,IP
- 网站流量监控方面
- 1、PV:查看了页面就+1 ----string incr
- 2、UV:不同用户访问,只有不同用户才+1,set
- 3、IP:不同IP才+1,set
- 网站流量监控方面
- 黑白名单
- sorted_set应用场景
- 在set基础上主要应用点:需要排序/权重/优先级(优先级可由多个级别共同组成)
- 排行榜,投票,有优先级的任务。
各类型注意事项
- string类型注意事项
- 数据操作成功与否和数据操作正常返回之间的差异
- (integer)0:false
- (integer)1:true
- 如上是操作失败和成功,strlen命令返回1的话代表正常返回,所以0,1代表成功还是失败还要参照具体执行的命令。
- 未获取到数据返回nil
- string 类型数据最大存储量521M
- string类型数字范围(正负)java.lang.Long.MAX_VALUE
- 数据操作成功与否和数据操作正常返回之间的差异
- hash类型注意事项
- 使用json还是hash结构存储值
- 上面提到user:id里的几个属性可以分开存,也可以放在一个json字符串里存,当然也可以放在一个hash结构里,只不过在于业务的需求,选择一种合适的方式即可。json存放,如果要修改其中某一个数据有点麻烦,如果数据不需要实时刷新,我们可以定时刷新里面数据即可。hash存放,可以实时修改里面某个属性的值。
- hash结构中属性的多少时的结构差异
- 存储少量属性:使用类数组结构
- 存储大量属性:使用hashmap结构
- hash类型的value只能存储字符串,不允许存储其它数据类型,不存在嵌套现象。
- hash中最多只能存储2的32次方-1个键值对
- hash类型十分贴近对象的存储结构,可方便对属性进行增加和删除,但它并非为对象而生,不能滥用。
- hgetall获取所有属性,入股属性过多会导致效率低下,慎用。
- 使用json还是hash结构存储值
- list数据类型
- 存储结构:底层使用双向链表结构,正因为是双向列表,所以既可以从左进左出,右进右出,故有如下命令
- lpush
- rpush
- lpop
- rpop
- 获取数据(0代表第一个,-1代表倒数第一个,-2代表倒数第二个)
- lrange
- lindex
- llen
- list扩展:指定时间内获取并移除数据
- blpop key1 [key2] timeout
- brpop key1 [key2] timeout
- brpoplpush source destination timeout
- b表示block,阻塞,阻塞期间如果list中有数据或者新存入了数据,就读取并删除。
- lrem key count value
- 左边删除count个value(list是允许value重复的,故有count表示个数值)
- list类型注意事项(应用于操作先后顺序的的业务数据)
- value只能是string,最多只能存储2的32次方-1个值
- list实现底层是双向链表(读取速度稍慢),可左右进出,操作方式可以是队列或者栈(左进左出---->先进先出)
- -1表示倒数第一个值
- 分页,第一个在redis中,后续再数据库中查询(第一页看的比较多,后面页看的较少的时候)
- 存储结构:底层使用双向链表结构,正因为是双向列表,所以既可以从左进左出,右进右出,故有如下命令
- set类型
- 命令
- sadd key member [member…]
- smembers key
- srem key member1 [member2…]
- scard key 获取集合数据总量
- sismember key member 判断集合中是否包含指定数据
- 随机取/随机取并移除
- srandmember key count 随机取
- spop key count 随机取并移除
- 命令
- sorted_set类型(set的基础上添加了排序,存储时指定score的值进行排序,注意score并不是指,只用于排序而已)
- 存储、取、删除、升序显示(默认)、降序显示(zrevrange)、是否显示score(withscores)
- sorted_set中score值的获取和修改
- zscore key member
- zincrby key increment member 可应用于投票和排序
redis适用场景
- 创建数据库表id,支持分表以及数据库集群
- 把string类型的数字当做整型处理,incr自增得表id
- 控制热点事物的时效性,通过数据是否失效控制业务行为
- 热点新闻多久失效,SETEX
- 微信投票时效性,SETEX
- 微信投票,规定每四个小时只能,记录投票用户id,设置过期时间为四小时。
- 高频,热点信息
- 新浪微博明星主页
- 头条热点新闻
- 百度头条新闻,热点新闻排行榜