关于redis的重点知识

1.Redis为什么是单线程、及⾼并发快的原因

  • redis是基于内存的,内存的读写速度常快;
  • redis是单线程的,省去了很多上下切换线程的时间;而且单线程的情况下,就不⽤去考虑各种锁的问题
  • (直接原因)redis使⽤IO多路复+epoll函数,可以处理并发的连接。阻塞IO 内部实现采epoll,采epoll+⾃⼰实现的简单的事件框架。epoll中的读、写、关闭、连接都转化成了事件,然后利epoll的多路复特性,绝不在io上浪费点时间

2Redis中的持久化方式(持化双雄)

RDB

在指定间隔时间内将内存的数据集快照写入硬盘,在恢复时再将硬盘快照文件直接读回内存(dump.rdb文件)

自动触发:间隔时间

手动触发:默认异步bgsave,阻塞save

优势:业务定时备份,适合大规模数据恢复,速度比AOF

弱势:最近数据会丢失,相当于克隆了一份数据,2被内存

AOF

以日志形式记录每一个写操作的指令,redis启动时候会根据日志内容将指令再执行一遍(默认不开启),保存在appendonly.aof文件中

三种策略:

Aways:同步写,每一个写命令执行完立即同步日志写回磁盘

Everysec(默认):将执行同步到日志(AOF文件缓冲区)每隔一秒写回磁盘

No:将执行同步到日志(AOF文件缓冲区),由操作系统决定写回磁盘

优势:更好保护数据不丢失,性能高

弱势:aof文件远大rdb,而且恢复速度慢

AOF重写机制:对aof文件内容的压缩

RDB+AOF结合:RDB做全量持久化,AOF做增量持久化

缓存三问

3.redis中的事务

Redis单线程体现出事务,按顺序串行化执行而不被其他命令插入

MULTI命令开启事务,将命令入队到事务中,由EXEC命令开始执行事务

4.如何优化频繁命令带来的性能下降(redis管道)

5.redis的主从复制

Master以写为主,Slave以读为主,当master数据更改时,数据会异步更新到其他slave数据库中,实现读写分离

使用:配从不配主

例:一主二从

  • 配置(配主不配从)
  • 启动连接到master主机
  • 首次全量复制(master主机进行RDB快照写入硬盘,slave从机再执行RDB快照文件)
  • 心跳保持(10秒)保持通信
  • 增量复制(将修改命令发送给slave从机)

6.redis哨兵(不存放数据)

监控master主机,当主机发生故障,会根据投票数选出一个从机成为主机。

哨兵一般为奇数

例:一主二从三哨兵

  • Master主观下线/客观下线
  • Raft算法选出新主机
  • 其他slave更换新主机
  • 老主机回来也是从机

7.集群

槽位-分片

Redis集群有16384个槽位,将槽位分段分入不同节点(分片)

例:三节点各一主一从(6redis实例服务,三主三从)

扩容,从原有的槽段(三各节点),各分配一些给新的节点,无需重新分配

缩小,将要删除的节点所拥有槽段全部给其他节点的其中一个

springboot连接集群

8.redis单线程+多线程(默认关闭)

原因:redis性能瓶颈是内存或网络宽带

Redis4:使用异步操作删除大key

Redis6/7:主线程和IO线程协同完成请求处理

IO线程:使用IO多路复用,使得一组线程可以处理多个tcp连接,读取socket,解析socket,写入socket(处理网络请求)

主线程:执行操作(命令的执行),避免上下文切换

9.bigkey

10.缓存穿透

原因:大量请求缓存中不存在的数据,导致所有请求都打到了数据库,数据库短时间内承受大量的请求而崩掉

解决方案:

  • 如果查询的数据确实不存在于数据库中,也将这个空结果缓存起来,设置一个较短的过期时间,避免频繁查询数据库(缺陷,只能适用相同key)
  •  (使用布隆过滤器)用于判断一个元素是否存在于一个集合中。在缓存层之前使用布隆过滤器,可以快速

滤掉那些明显不在数据库中的请求。如果布隆过滤器认为请求的数据可能存在,才会允许请求继续访问缓存或数据库

11.缓存击穿

原因:大量用户同时访问一条缓存中没有也可能是缓存过期了而去访问数据库,大量请求查询同个key

  • 设置热点数据永不过期:对于一些非常热门的数据,可以将其缓存设置为永不过期,保证即使过期失效,也会在后续请求中自动重新加载缓存。
  • 加互斥锁:在缓存失效时,加一步通过加锁的方式,第一个获取锁后,进行查询数据库并更新,其他现在在等待只允许一个请求去查询数据库并重新设置缓存,其他请求等待此请求完成后,直接从缓存中获取数据。

12.缓存雪崩

原因:

①缓存雪崩是指在缓存中大量的数据(key)同时过期失效,而此时又有大量的请求访问这些数据,导致所有请求都直接访问数据库,造成数据库瞬时压力过大,甚至崩溃

  • Redis主机眈机了

解决方案:①设置缓存数据的过期时间加上随机值,避免大量数据在同一时刻过期失效,(错开过期时间)或者设置永不过期

13.缓存一致性问题

不选择更新缓存原因:每一次更新数据库都要对应更新缓存,太多无效操作了,而

采用每次更新数据库就删除缓存,等需要访问的时候再更新缓存

  • 双检加锁策略

多个线程查询数据库这条数据,第一个数据查询到数据进行加锁,直到数据查询完并进行缓存后释放锁,其他线程就走redis缓存

  • 延时双删

先对redis缓存进行删除,再更新mysql中数据

(mysql更新数据这段时间还没commit,可能有其他线程查询到并写入缓存所以是旧值)

线程sleep小段时间(时间大于mysql更新时间),再对缓存可能存在的旧值进行删除

  • 异步更新缓存

先删除mysql数据,再删除缓存

(如果删除失败,将失败信息发送至消息队列,重复删除操作,达到一定次数无法超过删除,则运维参入)

14.基本数据类型(5

String(字符串):keyvalues

内部实现:int SDS(文本数据以及二进制文件视频,图片等)

应用场景:缓存对象;常规计数;分布式锁的实现

List(列表):keyvalues

内部实现:双向链表+压缩列表(元素个数<512,单元素<64字节)

3.2版本后quickList数据结构

应用场景:消息队列

Hash(哈希):还是kv,但是v是一个键值对

内部实现:压缩列表(与上面一致)+哈希表

7.0版本后用listpack

适用场景:缓存对象;购物车key(用户):[field(商品):values(数量)];分布式锁实现可重入

Set(集合):单值多values,不可重复

内部实现:哈希表和整数集合(上面)

适用场景:统计(点赞,共同关注);抽奖活动

Zset(有序集合):set的基础上加score分数,根据这个排序

内部实现:listpack

适用场景:排行榜,电话排序

15.redis分布式锁(多个JVM虚拟机)

插入SETNX和释放EXPIRE

适用分布式场景+AQS+防止死锁+可重入锁考虑+lua脚本+redis命令

=redis分布式锁

代码测试:(qiantuikeji.lock

缺点:满足APC不满足(当master宕机时,没有及时把数据写入从机,从机上位,不含该数据)

具备:独占性+高可用+不乱抢+防死锁+可重入

核心思想:我们利用redis setNx 方法,当有多个线程进入时,我们就利用该方法,第一个线程进入时,redis 中就有这个key 了,返回了1,如果结果是1,则表示他抢到了锁,那么他去执行业务,然后再删除锁,退出锁逻辑,没有抢到锁的哥们,等待一定时间后重试即可

防死锁:同时增加过期时间,防止死锁,

独占性:

高可用:Lua脚本解决多条命令原子性问题

不乱抢:

防死锁:

可重入:

16.布隆过滤器

原理:是一个大型的位数组,初始状态为均为0,当添加key的时候,计算该keyhashcode值所对应索引位置是否为0,为空则将0改为1;当查询的key的时候,会对key进行hashcode计算,如果计算所在索引位置为0,则不存在

不精确:因为不同key计算的hashcode值可能相等

17.如何提高redis性能

①将要执行的命令一批一批进行,选择恰当的持久化工作

9.redis的缓存场景

用户登录信息,商品信息,订单信息等

10.内存淘汰策略

当redis内存达到设置阈值时,Redis主动挑选部分key删除来释放内存。

Redis具有八中淘汰策略

1-2:不删;删有效期最短的

3-4:全部里面随机删;有ttl里面随机删

5-6:删全部里面最久没有访问;删有ttl里面最久没访问

7-8:删全部里面使用频率最少的;删有ttl里面使用频率最小的。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值