面试题精选与数据库对比
本教程共 40 篇 · 第 40 篇 · 更新于 2026-08-02
40. 面试题精选与数据库对比
走到第 40 章,你已具备完整的 Redis 知识体系。「码上学」把这一章当作「收口」:一侧是面试常被追问的高频题与标准答法,另一侧是和竞品的横向对比——前者帮你把知识讲清楚,后者帮你在选型会上做决策。建议结合前 39 章回头查漏补缺。
本节目标
- 掌握 Redis 高频面试题的作答要点(性能、持久化、缓存问题、锁、集群等)。
- 清晰表述 Redis 与 Memcached 的差异与适用边界。
- 说清 Redis 与关系型数据库、MongoDB 的定位区别,避免「误用」。
- 形成「什么场景选什么存储」的判断框架。
一、高频面试题精选
Q1:Redis 为什么这么快? 纯内存操作;单线程避免了锁竞争与上下文切换;基于 epoll/kqueue 的 I/O 多路复用,单线程也能扛数万连接;精雕细琢的数据结构(跳表、压缩列表/listpack、字典等);RESP 协议解析开销极低。
Q2:Redis 有哪些数据类型? 经典 5 种:String、Hash、List、Set、Sorted Set;扩展类型:Bitmap(基于 String)、HyperLogLog、GEO(基于 Sorted Set)、Stream;Redis 8.x 还内置了 JSON、向量集与多种概率类型(Bloom、Cuckoo、T-Digest、Top-K)。选型的本质是「用对结构」,例如排行榜用 Sorted Set,签到用 Bitmap,UV 用去重类概率结构。
Q3:RDB 和 AOF 有什么区别?怎么选? RDB 是某一时刻的内存快照,文件紧凑、恢复快、对性能影响小,但可能丢失最后一次快照之后的数据。AOF 记录每条写命令,数据更完整(默认 everysec 最多丢 1 秒),但文件更大、恢复更慢。Redis 4.0+ 支持混合持久化,兼顾两者。生产推荐 RDB + AOF 同时开启,恢复时优先 AOF。
Q4:缓存穿透、击穿、雪崩是什么?怎么解决? 穿透=查不存在的数据直击数据库,用布隆过滤器或缓存空对象;击穿=热点 key 过期瞬间并发打库,用互斥锁或热点不过期;雪崩=大量 key 同时失效或 Redis 宕机,用过期间加随机抖动、多级缓存、高可用架构、熔断降级。详见第 39 章。
Q5:怎么用 Redis 实现分布式锁?
用 SET key value NX EX seconds 一条命令原子地抢锁并设过期,value 用随机 token;释放必须用「比对 token 再删除」的 Lua 脚本,防止误删他人锁。对强一致要求极高的场景,社区更倾向 ZooKeeper/etcd。
Q6:Redis 事务支持回滚吗?
不支持。MULTI/EXEC 保证命令按序、不被插队执行(原子性排队),但若某条命令出错,已执行的不会回滚。需要「读-改-写」原子可用 WATCH(乐观锁)或 Lua 脚本。
Q7:Pipeline 和事务有什么区别? Pipeline 是把多条命令打包一次网络往返,减少 RTT、提升吞吐,但命令之间不保证原子、可能被其他客户端插入。事务则保证命令队列连续执行。要原子性请选事务或 Lua。
Q8:Redis 的内存淘汰策略有哪些?
noeviction(默认,写满报错)、allkeys-lru、allkeys-lfu、allkeys-random、volatile-lru、volatile-lfu、volatile-random、volatile-ttl。纯缓存推荐 allkeys-lru 或 allkeys-lfu(LFU 更能反映真实热度)。
Q9:键过期了为什么内存没立刻释放?
过期删除采用「惰性删除 + 定期删除」:访问时才惰性清理,后台定期抽样清理。大 key 及时删除建议用 UNLINK(异步)而非 DEL(同步阻塞)。
Q10:Redis Cluster 为什么是 16384 个槽?
Cluster 把数据按 CRC16(key) % 16384 映射到 16384 个哈希槽,槽分配到各主节点,扩缩容就是迁移槽。槽数适中:既能均匀分片,又让槽的元信息足够小、便于在节点间传播。
Q11:什么是脑裂?怎么缓解?
网络分区下旧主仍接写、哨兵已选新主,网络恢复后旧主降为从、分区数据被清。可用 min-replicas-to-write 与 min-replicas-max-lag 限制「与多数从断连时拒绝写入」,降低数据丢失。
Q12:Redis 是单线程,怎么利用多核? 单实例只用一核。可在单机起多实例,或用 Cluster 把槽分散到多节点;重计算(复杂 Lua)尽量下沉到客户端。
二、Redis vs Memcached
| 维度 | Redis | Memcached |
|---|---|---|
| 数据结构 | 丰富(String/Hash/List/Set/Sorted Set/Stream 等) | 仅简单键值(字符串) |
| 持久化 | 支持 RDB + AOF,重启可恢复 | 不支持,重启即丢 |
| 内存管理 | 灵活,支持淘汰策略(LRU/LFU 等) | 全内存,无淘汰,满则无法写入 |
| 线程模型 | 单线程 + 多路复用(网络/后台有额外线程) | 多线程,高并发靠线程池 |
| 高可用 | 主从、哨兵、Cluster | 无内置复制与故障转移 |
| 适用 | 缓存、队列、锁、排行榜等复杂场景 | 纯简单键值缓存、追求极致轻量 |
结论:功能性与可靠性要求高选 Redis;只是简单键值、追求最轻量的纯缓存,Memcached 仍有其位置。
三、Redis vs 关系型数据库
| 维度 | Redis | 关系型数据库(MySQL 等) |
|---|---|---|
| 存储位置 | 内存为主(可持久化到磁盘) | 磁盘为主 |
| 数据模型 | 键值 + 多种结构 | 表、行、列、SQL |
| 查询能力 | 结构简单检索,无复杂 SQL/联表 | 强大 SQL、索引、联表、聚合 |
| 性能 | 极高(十万级 QPS) | 受磁盘与锁限制,相对低 |
| 事务 | 单实例排队、不回滚 | 完整 ACID、可回滚 |
| 定位 | 缓存、热点、计数器、队列、锁 | 真实数据源、复杂业务 |
二者是互补而非替代:Redis 做前置缓存与高速中间件,关系库做权威存储与复杂查询。
四、Redis vs MongoDB
| 维度 | Redis | MongoDB |
|---|---|---|
| 数据模型 | 键值 + 多结构 | 文档(BSON,类 JSON,可嵌套) |
| 查询 | 简单检索,无完整查询语言 | 丰富查询、索引、聚合管道、正则 |
| 持久化 | RDB/AOF | 写时复制日志,落盘可靠 |
| 事务 | 单实例非严格事务 | 多文档 ACID 事务 |
| 扩展 | 主从/Cluster 分片 | 原生分片集群,水平扩展强 |
| 定位 | 高速缓存、实时中间件 | 复杂文档存储、大规模数据集 |
结论:需要高性能键值/缓存/实时能力选 Redis;需要存储复杂文档、做丰富查询与分析选 MongoDB。二者也常组合:MongoDB 存文档,Redis 缓存热点。
五、选型一句话框架
先问三个问题:数据要不要持久且复杂查询?要强事务吗?要的是速度还是结构? 答案指向「关系库/MongoDB 做源,Redis 做加速层」是最常见的正确组合。别用 Redis 硬扛它不擅长的复杂分析,也别用关系库去顶高频热点读。
提示:本章正文统一以 Redis 8.x(最新稳定版) 表述。需补充的是,官方 redis.io 下载页另将 8.8 标注为 “Latest stable”,而 GitHub 上 redis/redis 的最新发布 tag 为 8.10.0;二者同属 8.x 系列,本章涉及的命令与对比结论对教材内容没有影响。