Redis高频面试题整理
整理总结常见的Redis面试题,题目来自网络
-
什么是 Redis?
Redis是一个C语言开发的数据库,与传统数据库不同的是,Redis的数据是存在内存中的,所以读写速度非常快,被广泛用于缓存方向。当然Redis除了可以做缓存,还能用于做分布式锁,甚至消息队列(不过一般不用Redis做消息队列),Redis还提供了多种数据类型来支持不同的业务场景。Redis还支持事务、持久化、Lua脚本、集群。
-
Redis 有哪些数据类型?
string、list、hash、set、sorted set、bitmap、HyperLogLog。
string:简单的key-value类型。一般用于需要计数的场景,比如用户访问次数、热点文章点赞转发数
list:双向链表。可以实现消息队列。
hash:类似JDK1.8之前的HashMap,适合存储对象。
set:类似HashSet,但是是无需的。存放数据不能重复。
sorted set:与set相比,增加了权重参数score,使得集合中的元素能够按score进行有序排列。适合需要对数据根据权重排序的场景。
bitmap:存二进制数字。适合保存状态信息(是否签到,是否登录等)
HyperLogLogs:可以用于统计网站访问量
-
Redis 是单线程还是多线程?
Redis是单线程的。
追问:单线程如何处理高并发?1. Redis数据是在内存中的,计算也是在内存中的,非常快。2. Redis使用了NIO。3. Redis会给客户端指令通过队列来排队进行顺序处理。5. Redis的响应也有一个响应队列。
-
Redis 过期删除策略讲一下。
主要有2个策略。1、惰性删除。客户端访问的时候,判断一下有没有过期,如果过期了,就删除。2、定期删除。每隔一段时间抽取一批key执行删除过期key操作。
-
Redis 的持久化策略了解嘛?分别介绍下 RDB 和 AOF。
Redis有两种持久化策略。1、快照(RDB)。创建快照获得存储在内存里面的数据在某个时间点上的副本。2、只追加文件(AOF)。每执行一条更改Redis中的数据的命令,Redis就会将该命令写入硬盘中的AOF文件。
-
Redis 的缓存更新策略了解嘛?
主要有三种。1、LRU、LFU、FIFO算法。当缓存使用量达到阈值的时候,根据算法删除现有缓存。2、超时删除。给缓存设置过期时间,超时后自动删除。3、主动更新。主动更新缓存。
-
什么是缓存穿透?什么是缓存击穿?什么是缓存雪崩?怎么解决(最高频问题)
缓存穿透(击穿):数据不在缓存中,导致数据直接请求了数据库,根本没有经过缓存。解决方案:做好参数校验,不合法参数请求直接抛出异常返回给客户端。还可以使用布隆过滤器,把可能的请求值都存放在布隆过滤器中,当用户请求过来,先判断用户发送的请求是否存在于布隆过滤器中。
缓存雪崩:缓存在同一时间大面积失效,请求直接访问了数据库。解决方案:采用Redis集群以及限流,让热点缓存永不失效。
-
设计一个分布式锁?
线程占位,当别的线程进来操作,发现已经有线程占位了,就会放弃。比如访问前set k1 v1,过期时间为5秒,访问结束删除k1。当其他线程访问的时候,先尝试获取k1,如果能获取到,说明有线程正在临界区,阻塞等待。当然这个做法存在问题,因为过期时间为一个数,如果所用的操作时间大于这个时间,那么会因为超时而自动删除。一个解决思路是将锁的value设置为一个随机字符串,每次释放锁的时候,都去比较随机字符串是否一致,一致再释放(需要引入Lua脚本)。
-
Redis 缓存失效策略?
缓存淘汰策略。6种。最常用的是移除最近最少使用的key。
-
Redis 事务你了解嘛?
Redis事务不具备原子性(不支持回滚),只能确保当前事务不被其他事务打断。
-
如何保证 Redis 和 MySQL 的数据一致性?(如果项目同时用到 Redis 和 MySQL,这个问题特别容易被问)
3种缓存读写策略保证一致性。
- 旁路缓存模式。适合读请求比较多的场景。简单来说就是以数据库的数据为准。读的时候,如果缓存中有数据,那么直接从缓存中读;如果缓存中没有数据,那么先更新数据库,再把数据写入缓存。写的时候,先更新数据库,再删除缓存。
- 读写穿透。以缓存的数据为准。实际开发中不常用。读操作,如果缓存中有数据,那么直接从缓存中读;读不到数据则从数据库中读取,然后写入缓存。写操作,若缓存中没有,则更新数据库;反之,则先更新缓存再更新数据库。
- 异步缓存写入。与读写穿透类似,但是是异步更新数据库的。也就是说先更新缓存,再异步批量更新数据库。