admin管理员组文章数量:1794759
史上最全Redis面试题,看完这篇完全可以吊打面试官!
我是猿人,一个热爱技术、热爱编程的IT猿。技术是开源的,知识是共享的!
写作是对自己学习的总结和记录,如果您对 Java、分布式、微服务、中间件、Spring Boot、Spring Cloud等技术感兴趣,可以关注我的动态,我们一起学习,一起成长!
用知识改变命运,让家人过上更好的生活,互联网人一家亲!
---公众号「猿码天地」
Java知识学堂:gitee/zhangbw666/it-knowledge
你多学一样本事,就少说一句求人的话,现在的努力,是为了以后的不求别人,实力是最强的底气。记住,活着不是靠泪水博得同情,而是靠汗水赢得掌声。——《写给程序员朋友》
什么是 Redis?Redis 是完全开源免费的,遵守 BSD 协议,是一个高性能的 key-value 数据库。
Redis 与其他 key - value 缓存产品有以下三个特点:
(1)Redis 支持数据的持久化,可以将内存中的数据保存在磁盘中,重启的时候可以再次加载进行使用。
(2)Redis 不仅仅支持简单的 key-value 类型的数据,同时还提供 list,set,zset,hash 等数据结构的存储。
(3)Redis 支持数据的备份,即 master-slave 模式的数据备份。
Redis 优势
(1)性能极高 – Redis 能读的速度是 110000 次/s,写的速度是 81000 次/s 。
(2)丰富的数据类型 – Redis 支持二进制案例的 Strings, Lists, Hashes, Sets 及Ordered Sets 数据类型操作。
(3)原子 – Redis 的所有操作都是原子性的,意思就是要么成功执行要么失败完全不执行。单个操作是原子性的。多个操作也支持事务,即原子性,通过 MULTI 和 EXEC指令包起来。
(4)丰富的特性 – Redis 还支持 publish/subscribe, 通知, key 过期等等特性。
Redis 与其他 key-value 存储有什么不同?
(1)Redis 有着更为复杂的数据结构并且提供对他们的原子性操作,这是一个不同于其他数据库的进化路径。Redis 的数据类型都是基于基本数据结构的同时对程序员透明,无需进行额外的抽象。
(2)Redis 运行在内存中但是可以持久化到磁盘,所以在对不同数据集进行高速读写时需要权衡内存,因为数据量不能大于硬件内存。在内存数据库方面的另一个优点是,相比在磁盘上相同的复杂的数据结构,在内存中操作起来非常简单,这样 Redis可以做很多内部复杂性很强的事情。同时,在磁盘格式方面他们是紧凑的以追加的方式产生的,因为他们并不需要进行随机访问。
Redis主要有哪些功能?哨兵(Sentinel)和复制(Replication)
Redis服务器毫无征兆的罢工是个麻烦事,如何保证备份的机器是原始服务器的完整备份呢?这时候就需要哨兵和复制。
Sentinel可以管理多个Redis服务器,它提供了监控,提醒以及自动的故障转移的功能,Replication则是负责让一个Redis服务器可以配备多个备份的服务器。
Redis也是利用这两个功能来保证Redis的高可用的。
事务
很多情况下我们需要一次执行不止一个命令,而且需要其同时成功或者失败。redis对事务的支持也是源自于这部分需求,即支持一次性按顺序执行多个命令的能力,并保证其原子性。
LUA脚本
在事务的基础上,如果我们需要在服务端一次性的执行更复杂的操作(包含一些逻辑判断),则lua就可以排上用场了。
持久化
redis的持久化指的是redis会把内存的中的数据写入到硬盘中,在redis重新启动的时候加载这些数据,从而最大限度的降低缓存丢失带来的影响。
集群(Cluster)
单台服务器资源的总是有上限的,CPU资源和IO资源我们可以通过主从复制,进行读写分离,把一部分CPU和IO的压力转移到从服务器上,这也有点类似mysql数据库的主从同步。
Redis支持哪几种数据类型?支持多种类型的数据结构
1.string:最基本的数据类型,二进制安全的字符串,最大512M。
2.list:按照添加顺序保持顺序的字符串列表。
3.set:无序的字符串集合,不存在重复的元素。
4.sorted set:已排序的字符串集合。
5.hash:key-value对的一种集合。
Redis是单进程单线程的?Redis是单进程单线程的,Redis利用队列技术将并发访问变为串行访问,消除了传统数据库串行控制的开销。
Redis为什么是单线程的?多线程处理会涉及到锁,而且多线程处理会涉及到线程切换而消耗CPU。因为CPU不是Redis的瓶颈,Redis的瓶颈最有可能是机器内存或者网络带宽。单线程无法发挥多核CPU性能,不过可以通过在单机开多个Redis实例来解决。
其它开源软件采用的模型Nginx:多进程单线程模型
Memcached:单进程多线程模型
使用Redis的优势? 1.速度快,因为数据存在内存中,类似于HashMap,HashMap的优势就是查找和操作的时间复杂度都是O(1) 2.支持丰富数据类型,支持string,list,set,sorted set,hash 3.支持事务,操作都是原子性,所谓的原子性就是对数据的更改要么全部执行,要么全部不执行 4.丰富的特性:可用于缓存,消,按key设置过期时间,过期后将会自动删除 Redis单点吞吐量单点TPS达到8万/秒,QPS达到10万/秒,补充下TPS和QPS的概念
1.QPS: 应用系统每秒钟最大能接受的用户访问量 每秒钟处理完请求的次数,注意这里是处理完,具体是指发出请求到服务器处理完成功返回结果。可以理解在server中有个counter,每处理一个请求加1,1秒后counter=QPS。 2.TPS: 每秒钟最大能处理的请求数 每秒钟处理完的事务次数,一个应用系统1s能完成多少事务处理,一个事务在分布式处理中,可能会对应多个请求,对于衡量单个接口服务的处理能力,用QPS比较合理。 Redis有哪几种数据淘汰策略?在Redis中,允许用户设置最大使用内存大小server.maxmemory,当Redis 内存数据集大小上升到一定大小的时候,就会施行数据淘汰策略。
1.volatile-lru:从已设置过期的数据集中挑选最近最少使用的淘汰 2.volatile-ttr:从已设置过期的数据集中挑选将要过期的数据淘汰 3.volatile-random:从已设置过期的数据集中任意挑选数据淘汰 4.allkeys-lru:从数据集中挑选最近最少使用的数据淘汰 5.allkeys-random:从数据集中任意挑选数据淘汰 6.noenviction:禁止淘汰数据 Redis集群方案应该怎么做?都有哪些方案?1.twemproxy ,Twemproxy 也叫 nutcraker。是 Twtter 开源的一个 Redis 和 Memcache 代理服务器,主要用于管理 Redis 和 Memcached 集群,减少与Cache 服务器直接连接的数量。
2.codis ,目前用的最多的集群方案,基本和twemproxy一致的效果,但它支持在 节点数量改变情况下,旧节点数据可恢复到新hash节点。
3.Redis cluster3.0自带的集群,特点在于他的分布式算法不是一致性hash,而是hash槽的概念,以及自身支持节点设置从节点。
Redis读写分离模型通过增加Slave DB的数量,读的性能可以线性增长。为了避免Master DB的单点故障,集群一般都会采用两台Master DB做双机热备,所以整个集群的读和写的可用性都非常高。
读写分离架构的缺陷在于,不管是Master还是Slave,每个节点都必须保存完整的数据,如果在数据量很大的情况下,集群的扩展能力还是受限于单个节点的存储能力,而且对于Write-intensive类型的应用,读写分离架构并不适合。
Redis数据分片模型为了解决读写分离模型的缺陷,可以将数据分片模型应用进来。
可以将每个节点看成都是独立的master,然后通过业务实现数据分片。
结合上面两种模型,可以将每个master设计成由一个master和多个slave组成的模型。
Redis提供了哪几种持久化方式?Redis提供两种持久化机制 RDB 和 AOF 机制。
1、RDB(Redis DataBase)持久化方式
是指用数据集快照的方式半持久化模式)记录 redis 数据库的所有键值对,在某个时间点将数据写入一个临时文件,持久化结束后,用这个临时文件替换上次持久化的文件,达到数据恢复。
优点:
(1)只有一个文件 dump.rdb,方便持久化。
(2)容灾性好,一个文件可以保存到安全的磁盘。
(3)性能最大化,fork 子进程来完成写操作,让主进程继续处理命令,所以是 IO最大化。使用单独子进程来进行持久化,主进程不会进行任何 IO 操作,保证了 redis的高性能)
(4)相对于数据集大时,比 AOF 的启动效率更高。
缺点:
数据安全性低。RDB 是间隔一段时间进行持久化,如果持久化之间 redis 发生故障,会发生数据丢失。所以这种方式更适合数据要求不严谨的时候
2、AOF(Append-only file)持久化方式
是指所有的命令行记录以 redis 命令请求协议的格式完全持久化存储)保存为 aof 文件。
优点:
(1)数据安全,aof 持久化可以配置 appendfsync 属性,有 always,每进行一次命令操作就记录到 aof 文件中一次。
(2)通过 append 模式写文件,即使中途服务器宕机,可以通过 redis-check-aof工具解决数据一致性问题。
(3)AOF 机制的 rewrite 模式。AOF 文件没被 rewrite 之前(文件过大时会对命令进行合并重写),可以删除其中的某些命令(比如误操作的 flushall))
缺点:
(1)AOF 文件比 RDB 文件大,且恢复速度慢。
(2)数据集大的时候,比 rdb 启动效率低。
Redis常见性能问题和解决方案? (1) Master最好不要做任何持久化工作,如RDB内存快照和AOF日志文件 (2) 如果数据比较重要,某个Slave开启AOF备份数据,策略设置为每秒同步一次 (3) 为了主从复制的速度和连接的稳定性,Master和Slave最好在同一个局域网内 (4) 尽量避免在压力很大的主库上增加从库 (5) 主从复制不要用图状结构,用单向链表结构更为稳定,即:Master <- Slave1 <- Slave2 <- Slave3… 这样的结构方便解决单点故障问题,实现Slave对Master的替换。如果Master挂了,可以立刻启用Slave1做Master,其他不变。 Redis支持的Java客户端都有哪些?官方推荐用哪个?Redisson、Jedis、lettuce等等,官方推荐使用Redisson。
Redis哈希槽的概念?Redis 集群没有使用一致性 hash,而是引入了哈希槽的概念,Redis 集群有16384 个哈希槽,每个 key 通过 CRC16 校验后对 16384 取模来决定放置哪个槽,集群的每个节点负责一部分 hash 槽。
Redis集群最大节点个数是多少?Redis集群预分好16384个桶(哈希槽)
Redis集群的主从复制模型是怎样的?为了使在部分节点失败或者大部分节点无法通信的情况下集群仍然可用,所以集群使用了主从复制模型,每个节点都会有N-1个复制品。
Redis集群会有写操作丢失吗?为什么?Redis并不能保证数据的强一致性,这意味这在实际中集群在特定的条件下可能会丢失写操作。
Redis集群之间是如何复制的?异步复制
Redis如何做内存优化?尽可能使用散列表(hashes),散列表(是说散列表里面存储的数少)使用的内存非常小,所以你应该尽可能的将你的数据模型抽象到一个散列表里面。比如你的web系统中有一个用户对象,不要为这个用户的名称,姓氏,邮箱,密码设置单独的key,而是应该把这个用户的所有信存储到一张散列表里面。
Redis回收进程如何工作的?一个客户端运行了新的命令,添加了新的数据。 Redis检查内存使用情况,如果大于maxmemory的限制, 则根据设定好的策略进行回收。
Redis回收使用的是什么算法?LRU算法
Redis有哪些适合的场景? 1)Session共享(单点登录) 2)页面缓存 3)队列 4)排行榜/计数器 5)发布/订阅 redis 过期键的删除策略?(1)定时删除:在设置键的过期时间的同时,创建一个定时器 timer). 让定时器在键的过期时间来临时,立即执行对键的删除操作。
(2)惰性删除:放任键过期不管,但是每次从键空间中获取键时,都检查取得的键是否过期,如果过期的话,就删除该键;如果没有过期,就返回该键。
(3)定期删除:每隔一段时间程序就对数据库进行一次检查,删除里面的过期键。至于要删除多少过期键,以及要检查多少个数据库,则由算法决定。
Redis 的同步机制了解么?Redis 可以使用主从同步,从从同步。第一次同步时,主节点做一次 bgsave,并同时将后续修改操作记录到内存 buffer,待完成后将 rdb 文件全量同步到复制节点,复制节点接受完成后将 rdb 镜像加载到内存。加载完成后,再通知主节点将期间修改的操作记录同步到复制节点进行重放就完成了同步过程。
Redis 集群方案什么情况下会导致整个集群不可用?有 A,B,C 三个节点的集群,在没有复制模型的情况下,如果节点 B 失败了,那么整个集群就会以为缺少 5501-11000 这个范围的槽而不可用。
Redis 如何设置密码及验证密码?设置密码:config set requirepass 123456 授权密码:auth 123456
Redis 集群如何选择数据库?Redis 集群目前无法做数据库选择,默认在 0 数据库。
Redis 事务相关的命令有哪几个?MULTI、EXEC、DISCARD、WATCH
Redis key 的过期时间和永久有效分别怎么设置?EXPIRE 和 PERSIST 命令。
Redis 的内存用完了会发生什么?如果达到设置的上限,Redis 的写命令会返回错误信(但是读命令还可以正常返回。)或者你可以将 Redis 当缓存来使用配置淘汰机制,当 Redis 达到内存上限时会冲刷掉旧的内容。
MySQL 里有 2000w 数据,redis 中只存 20w 的数据,如何保证 redis 中的数据都是热点数据? Redis 内存数据集大小上升到一定大小的时候,就会施行数据淘汰策略。 相关知识:Redis 提供 6 种数据淘汰策略: volatile-lru:从已设置过期时间的数据集(server.db[i].expires)中挑选最近最少使用的数据淘汰 volatile-ttl:从已设置过期时间的数据集(server.db[i].expires)中挑选将要过期的数据淘汰 volatile-random:从已设置过期时间的数据集(server.db[i].expires)中任意选择数据淘汰 allkeys-lru:从数据集(server.db[i].dict)中挑选最近最少使用的数据淘汰 allkeys-random:从数据集(server.db[i].dict)中任意选择数据淘汰 no-enviction(驱逐):禁止驱逐数据 假如 Redis 里面有 1 亿个 key,其中有 10w 个 key 是以某个固定的已知的前缀开头的,如何将它们全部找出来?使用 keys 指令可以扫出指定模式的 key 列表。
对方接着追问:如果这个 redis 正在给线上的业务提供服务,那使用 keys 指令会有什么问题?
这个时候你要回答 redis 关键的一个特性:redis 的单线程的。keys 指令会导致线程阻塞一段时间,线上服务会停顿,直到指令执行完毕,服务才能恢复。这个时候可以使用 scan 指令,scan 指令可以无阻塞的提取出指定模式的 key 列表,但是会有一定的重复概率,在客户端做一次去重就可以了,但是整体所花费的时间会比直接用 keys 指令长。
如果有大量的 key 需要设置同一时间过期,一般需要注意什么?如果大量的 key 过期时间设置的过于集中,到过期的那个时间点,redis 可能会出现短暂的卡顿现象(也有可能出现缓存雪崩)。一般需要在时间上加一个随机值,使得过期时间分散一些。
使用过 Redis 做异步队列么,你是怎么用的? 一般使用 list 结构作为队列,rpush 生产消,lpop 消费消。当 lpop 没有消的时候,要适当 sleep 一会再重试。如果对方追问可不可以不用 sleep 呢?list 还有个指令叫 blpop,在没有消的时候,它会阻塞住直到消到来。如果对方追问能不能生产一次消费多次呢?使用 pub/sub 主题订阅者模式,可以实现1:N 的消队列。 如果对方追问 pub/sub 有什么缺点? 在消费者下线的情况下,生产的消会丢失,得使用专业的消队列如 RabbitMQ等。 如果对方追问 redis 如何实现延时队列? 我估计现在你很想把面试官一棒打死如果你手上有一根棒球棍的话,怎么问的这么详细。但是你很克制,然后神态自若的回答道:使用 sortedset,拿时间戳作为score,消内容作为 key 调用 zadd 来生产消,消费者用 zrangebyscore 指令获取 N 秒之前的数据轮询进行处理。到这里,面试官暗地里已经对你竖起了大拇指。但是他不知道的是此刻你却竖起了中指,在椅子背后。 使用过 Redis 分布式锁么,它是什么回事?先拿 setnx 来争抢锁,抢到之后,再用 expire 给锁加一个过期时间防止锁忘记了释放。
这时候对方会告诉你说你回答得不错,然后接着问如果在 setnx 之后执行 expire之前进程意外 crash 或者要重启维护了,那会怎么样?这时候你要给予惊讶的反馈:唉,是喔,这个锁就永远得不到释放了。紧接着你需要抓一抓自己得脑袋,故作思考片刻,好像接下来的结果是你主动思考出来的,然后回答:我记得 set 指令有非常复杂的参数,这个应该是可以同时把 setnx 和expire 合成一条指令来用的!对方这时会显露笑容,心里开始默念:摁,这小子还不错。
福利一:月薪3万Java优秀简历模板
简历是对你过往学习和工作的一个总结,一份好的简历容易给人留下深刻印象,更容易被企业发现,创造更多的就业机会。优秀的简历可以把你推销给优秀的企业,看看别人的优秀简历范文,让自己的简历更加优秀吧。
获取方式:
微信搜索「猿码天地」或者扫描下面的二维码,关注后回复关键字「简历」即可获取!
福利二:全网最全一线大厂Java笔试面试题面试题涵盖了Spring核心知识、SpringMVC、SpirngBoot、SpringCloud、JVM、数据库、常用消组件Kafka、RabbitMQ、分布式、微服务组件Eureka、Ribbon、Config、Feign、Nacos、Zookeeper等、SQL优化、常用服务器Tomcat、Nginx、多线程、高并发等等。
部分截图:
获取方式:
微信搜索「猿码天地」或者扫描下面的二维码,关注后回复关键字「BAT面试」即可获取!
福利三:1000+本Java开发精华电子书猿人从事Java开发多年,从最初的小白,一步步通过自己不断的学习、摸索,终于走上了码农这条没有回头的路。学习是无止境的,有时零零散散的学习资料难以将我们的知识成体系的串联起来。为此,为了让大家在学习Java的道路上成系统的学习,少走弯路,猿人为大家整理了1000+本Java开发精华电子书,毕竟现在电子书也是挺贵的,哈哈,希望能给大家带来帮助。
电子书涵盖:Java入门、并发编程、底层、常用框架、性能优化、设计模式、工具、计算机网络、操作系统、数据库、数据结构与算法、大数据、架构设计、Linux知识、面试、扩展、管理、容器化技术、云计算、微服务、领域设计等方方面面,猿人还会给持续更新。
部分目录:
获取方式:
第一种:微信搜索「猿码天地」或者扫描下面的二维码,关注后回复关键字「电子书」即可获取!
第二种:Gitee:gitee/zhangbw666/java-books
希望程序员朋友能认真学习,根据自身需要获取对应的电子书,学习是永无止境的。
你多学一样本事,就少说一句求人的话,现在的努力,是为了以后的不求别人,实力是最强的底气。记住,活着不是靠泪水博得同情,而是靠汗水赢得掌声。——《写给程序员朋友》
版权声明:本文标题:史上最全Redis面试题,看完这篇完全可以吊打面试官! 内容由林淑君副主任自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:http://www.xiehuijuan.com/baike/1686561368a82078.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
发表评论