Redis总结

目录

一、基础概念类

[1.1、介绍一下什么是 Redis,有什么特点](#1.1、介绍一下什么是 Redis,有什么特点)

1、定义:

2、核心特点:

[1.2、Redis 为什么是单线程模型](#1.2、Redis 为什么是单线程模型)

1.3、Redis为什么把数据放到内存中

二、数据类型与底层实现类

2.1、Redis支持的数据类型和内部编码

1、数据类型

2、内部编码(由Redis自动切换)

[2.2、ZSet 为什么使用跳表,而不是红黑树](#2.2、ZSet 为什么使用跳表,而不是红黑树)

三、核心功能类

3.1、持久化机制

1、Redis持久化机制

2、RDB持久化触发条件

3、AOF文件同步策略

[4、AOF 的重写机制是怎样的](#4、AOF 的重写机制是怎样的)

3.2、主从复制

[1、Redis 的主从同步 / 主从复制是怎么回事](#1、Redis 的主从同步 / 主从复制是怎么回事)

2、主从复制的核心流程

3.3、哨兵模式

[1、介绍下 Redis 哨兵](#1、介绍下 Redis 哨兵)

2、哨兵发现主节点宕机后,会做哪些事情

3.4、集群模式

[1、Redis 的集群是干什么的](#1、Redis 的集群是干什么的)

[2、Redis 的哈希槽是怎么回事](#2、Redis 的哈希槽是怎么回事)

[3、Redis 集群的最大节点个数是多少](#3、Redis 集群的最大节点个数是多少)

[4、Redis 集群会有些操作丢失吗](#4、Redis 集群会有些操作丢失吗)

[5、Redis 集群如何选择数据库](#5、Redis 集群如何选择数据库)

四、应用场景类

[4.1、Redis 的常见应用场景有哪些](#4.1、Redis 的常见应用场景有哪些)

[4.2、如何使用 Redis 作为消息队列](#4.2、如何使用 Redis 作为消息队列)

[4.3、如何使用 Redis 实现分布式锁](#4.3、如何使用 Redis 实现分布式锁)

五、缓存相关问题类

5.1、什么是缓存穿透、缓存雪崩、缓存击穿

5.2、缓存穿透、雪崩、击穿的解决方案

1、缓存穿透

2、缓存雪崩

3、缓存击穿

5.3、缓存更新策略

5.4、Redis淘汰策略

六、命令与操作类

[6.1、怎样测试 Redis 服务器的连通性](#6.1、怎样测试 Redis 服务器的连通性)

[6.2、如何设置 key 的过期时间](#6.2、如何设置 key 的过期时间)

[6.3、为什么在生产环境上不应该使用 keys * 命令](#6.3、为什么在生产环境上不应该使用 keys * 命令)

[6.4、Redis 的常用管理命令有哪些](#6.4、Redis 的常用管理命令有哪些)

[6.5、Redis 的 pipeline(流水线)是什么](#6.5、Redis 的 pipeline(流水线)是什么)

[6.6、Redis 如何遍历 key](#6.6、Redis 如何遍历 key)

七、其他问题

[7.1、Redis 和 MySQL 如何保证双写一致性](#7.1、Redis 和 MySQL 如何保证双写一致性)

[7.2、什么是 Redis 的 "bigkey" 问题?如何解决](#7.2、什么是 Redis 的 “bigkey” 问题?如何解决)

[7.3、如何实现 Redis 高可用](#7.3、如何实现 Redis 高可用)

[7.4、什么是热 key 问题?如何解决](#7.4、什么是热 key 问题?如何解决)

[7.5、如何理解 Redis 的事务?和 MySQL 的事务有啥区别](#7.5、如何理解 Redis 的事务?和 MySQL 的事务有啥区别)

[1、Redis 事务本质:](#1、Redis 事务本质:)

[2、与MySQL 事务的区别](#2、与MySQL 事务的区别)

3、相关命令:

[7.6、Redis 用到的网络通讯协议是怎样的](#7.6、Redis 用到的网络通讯协议是怎样的)

[7.7、Redis 如何实现 "查找附近的人"?](#7.7、Redis 如何实现 “查找附近的人”?)

7.8、Redis中的IO多路复用是怎么回事

7.9、Redis的key的过期删除策略


一、基础概念类

1.1、介绍一下什么是 Redis,有什么特点
1、定义:

高性能的 key-value 内存数据库,以键值对形式存储数据,支持持久化到硬盘,不依赖 "表" 结构,核心优势是简单易用和高性能。

2、核心特点:
  • 纯内存存储,读写速度极快;
  • 支持字符串、哈希、列表等多种数据结构;
  • 支持 RDB 和 AOF 两种持久化方式;
  • 单线程处理命令(6.0 后多线程处理网络 / IO,命令执行仍单线程);
  • 支持主从复制、哨兵模式、集群部署;
  • 支持事务、Lua 脚本、多语言客户端;
  • 提供键过期、发布订阅、流水线等附加功能。
1.2、Redis 为什么是单线程模型

核心逻辑简单,性能瓶颈多在内存或 IO,而非 CPU,多线程无明显收益;

避免多线程带来的线程安全问题和线程切换开销;

6.0 后引入多线程优化:仅用于处理网络请求和协议解析,命令执行仍保持单线程,提升 IO 处理效率。

1.3、Redis为什么把数据放到内存中

**核心原因:**内存访问速度远超硬盘(内存随机访问约 100ns,硬盘随机访问约 10ms),直接奠定高性能基础;

**补充:**内存数据易丢失,因此通过 RDB/AOF 持久化机制备份到硬盘,兼顾性能和数据安全性。

二、数据类型与底层实现类

2.1、Redis支持的数据类型和内部编码

详细内容见:https://blog.csdn.net/yiting2580/article/details/156981199?fromshare=blogdetail&sharetype=blogdetail&sharerId=156981199&sharerefer=PC&sharesource=yiting2580&sharefrom=from_link

1、数据类型

核心 5 种: 字符串(string)、哈希(hash)、列表(list)、集合(set)、有序集合(zset)

扩展类型:Bitmap(位图)、HyperLogLog(基数统计)、GEO(地理信息)、Stream(消息队列)

2、内部编码(由Redis自动切换)
2.2、ZSet 为什么使用跳表,而不是红黑树

两者时间复杂度一致(插入 / 查询 / 删除均为 O (logN));

跳表实现更简单,无需红黑树的平衡调整操作,更适合 Redis 的设计理念。

三、核心功能类

3.1、持久化机制

详细内容见:https://blog.csdn.net/yiting2580/article/details/157182998?fromshare=blogdetail&sharetype=blogdetail&sharerId=157182998&sharerefer=PC&sharesource=yiting2580&sharefrom=from_link

1、Redis持久化机制

两种方式:RDB(快照持久化)和 AOF(日志持久化)

2、RDB持久化触发条件

手动触发:执行 save(阻塞主进程)或 bgsave(创建子进程,非阻塞)命令

自动触发:配置文件;主从复制;关闭Redis

生成 RDB 期间,Redis 是否可以处理写请求

  • save命令:阻塞主进程,无法处理写请求;
  • bgsave 命令:创建子进程生成 RDB,主进程正常处理写请求,新写入数据不会同步到本次 RDB,需下次触发 RDB 时持久化。
3、AOF文件同步策略
4、AOF 的重写机制是怎样的
  • 目的:压缩 AOF 文件体积,去除无效命令、合并重复命令;
  • 触发方式:手动执行 bgrewriteaof 命令,或通过 auto-aof-rewrite-min-size(默认 64MB)和 auto-aof-rewrite-percentage 自动触发;
  • 核心逻辑:子进程基于当前内存数据生成新 AOF 文件,主进程将重写期间的修改写入缓冲区,重写完成后合并缓冲区数据到新文件,替换旧文件。
3.2、主从复制

详细内容见:https://blog.csdn.net/yiting2580/article/details/157213747?fromshare=blogdetail&sharetype=blogdetail&sharerId=157213747&sharerefer=PC&sharesource=yiting2580&sharefrom=from_link

1、Redis 的主从同步 / 主从复制是怎么回事

核心作用: 提高可用性(主节点故障时从节点兜底)、分担读压力(主写从读);

实现方式 :从节点启动时通过 slaveof 命令指定主节点,自动清空自身数据并全量复制主节点数据,后续主节点数据修改会实时同步到从节点;

**特点:**主节点支持读写,从节点默认只读(slave-read-only=yes)。

2、主从复制的核心流程
  • 从节点保存主节点地址信息;
  • 建立 TCP 连接,发送 ping 命令验证主节点可用性;
  • 权限验证(主节点设密码时,从节点需配置 masterauth);
  • 数据同步(首次全量复制,后续部分复制);
  • 命令持续同步(主节点实时将修改命令发送给从节点)。
3.3、哨兵模式

详细内容见:https://blog.csdn.net/yiting2580/article/details/157292550?fromshare=blogdetail&sharetype=blogdetail&sharerId=157292550&sharerefer=PC&sharesource=yiting2580&sharefrom=from_link

1、介绍下 Redis 哨兵

定义: Redis 高可用解决方案,由多个哨兵节点组成,监控主从节点状态,自动完成故障发现和故障转移;

核心功能:

  • 监控:定期检测数据节点和其他哨兵节点是否可达;
  • 故障转移:主节点故障时,选举新主节点并维护主从关系;
  • 通知:将故障转移结果告知应用方。
2、哨兵发现主节点宕机后,会做哪些事情

**主观下线(SDOWN):**单个哨兵节点检测到主节点无心跳,标记为主观下线;

客观下线(ODOWN): 多个哨兵节点协商,达成法定票数(超过半数)后,标记主节点客观下线;

选举 leader 哨兵: 通过 Raft 算法选举一个哨兵节点作为 leader,负责后续故障转移;

故障转移执行:

  • 从所有从节点中筛选新主节点(优先级 ;复制偏移量 ;run id);
  • 让新主节点执行 slaveof no one,晋升为主节点;
  • 让其他从节点同步新主节点数据;
  • 原主节点恢复后,将其设为新主节点的从节点。
3.4、集群模式

详细内容见https://blog.csdn.net/yiting2580/article/details/149515003?fromshare=blogdetail&sharetype=blogdetail&sharerId=149515003&sharerefer=PC&sharesource=yiting2580&sharefrom=from_link

1、Redis 的集群是干什么的

核心目的: 解决单节点存储容量限制,实现数据分布式存储,同时保证高可用和扩展性;

**原理:**将数据分片存储在多个主节点上,每个主节点搭配从节点,主节点故障时从节点自动补位

2、Redis 的哈希槽是怎么回事

核心机制: Redis 集群将 16384 个哈希槽(0-16383)分配给各个主节点,每个主节点负责部分槽位;

分片规则: hash_slot = crc16(key) % 16384,根据键的哈希槽值确定存储的主节点;

**优势:**扩容 / 缩容时仅需迁移部分槽位数据,无需全量迁移,效率更高

3、Redis 集群的最大节点个数是多少

作者建议:不超过 1000 个主节点(基于哈希槽分配和集群稳定性考虑)

4、Redis 集群会有些操作丢失吗

Redis并不能保证数据的强一致性,在极端情况下可能会丢失写操作

比如:在写成功一个key之后,正好主节点宕机,此时由于这个数据还没有来得及同步到从节点上,也没来得及AOF写入日志,就丢失了 。

5、Redis 集群如何选择数据库

集群模式不支持选择数据库,仅能使用默认的数据库 0

四、应用场景类

4.1、Redis 的常见应用场景有哪些
  • 缓存:存储热点数据,降低数据库访问压力,加速读写;
  • 计数器:统计视频播放量、商品浏览数等,支持原子增减操作;
  • 排行榜:基于 zset 实现按热度、时间等维度的排行榜;
  • 分布式会话:集中存储用户登录信息,解决分布式系统会话共享问题;
  • 分布式锁:基于 setnx+ 过期时间 + Lua 脚本实现,控制分布式系统并发访问;
  • 消息队列:通过 List(阻塞队列)、Pub/Sub 或 Stream 实现简单消息队列;
  • 社交功能:实现点赞、粉丝、共同好友等功能(基于集合交集 / 并集操作);
  • 地理信息:基于 GEO 类型实现 "附近的人" 等 LBS 功能。
4.2、如何使用 Redis 作为消息队列
  • List 实现:生产者用 lpush/rpush 写入,消费者用**blpop/brpop**阻塞读取,适合简单队列场景;

  • Pub/Sub 实现:基于发布订阅模式,支持多消费者订阅,无消息持久化;

  • Stream 实现:Redis 5.0 新增,支持消息持久化、分组消费、ACK 机制,功能最完善。

4.3、如何使用 Redis 实现分布式锁

详细内容见:https://blog.csdn.net/yiting2580/article/details/157329306?fromshare=blogdetail&sharetype=blogdetail&sharerId=157329306&sharerefer=PC&sharesource=yiting2580&sharefrom=from_link

  • 加锁:set key 服务器ID NX EX 10s(key 为锁标识,NX 保证仅不存在时设置,EX 设过期时间防死锁)
  • 解锁:通过 Lua 脚本原子执行 "判断服务器 ID 一致→删除 key",避免误删其他节点的锁
  • 优化:
    • 看门狗(watch dog):加锁节点启动独立线程,定期为未完成的任务续期过期时间
    • Redlock 算法:向多个 Redis 节点加锁,超过半数节点加锁成功则视为锁生效,提升分布式场景下的可靠性

五、缓存相关问题类

详细内容见https://blog.csdn.net/yiting2580/article/details/157329306?fromshare=blogdetail&sharetype=blogdetail&sharerId=157329306&sharerefer=PC&sharesource=yiting2580&sharefrom=from_link

5.1、什么是缓存穿透、缓存雪崩、缓存击穿

缓存穿透: 访问的 key 在 Redis 和数据库中均不存在,导致请求直接穿透到数据库,持续占用数据库资源;

缓存雪崩: 短时间内大量 key 过期(或 Redis 宕机),缓存失效,大量请求直接冲击数据库;

缓存击穿: 热点 key 突然过期,大量并发请求直接访问数据库,导致数据库压力骤增。

5.2、缓存穿透、雪崩、击穿的解决方案
1、缓存穿透

严格校验请求参数(如手机号、ID 格式校验);

数据库不存在的 key 也存入 Redis(值设为空字符串),设置短期过期时间;

使用布隆过滤器预判 key 是否存在,不存在则直接返回。

2、缓存雪崩

部署高可用 Redis 集群(主从 + 哨兵),避免单点宕机;

key 过期时间添加随机因子(如原 1 小时过期,改为 50-70 分钟随机),分散过期时间;

核心业务 key 不设置过期时间。

3、缓存击穿

热点 key 设为永不过期;

访问数据库时加分布式锁,限制并发请求数;

服务降级:热点 key 过期时,返回默认数据或提示 "服务繁忙"。

5.3、缓存更新策略

**定期生成:**统计周期内热点数据,批量写入缓存(实时性低)

实时生成:

缓存未满:查询未命中时,从数据库加载数据并写入缓存;

缓存满时:触发淘汰策略删除旧数据,支持的策略包括 LRU(最近最少使用)、LFU(最近 最不常使用)、FIFO(先进先出)等。

5.4、Redis淘汰策略

**触发条件:**内存不足时,新增 key 会触发淘汰

核心策略:

  • 范围划分:volatile-* (仅淘汰带过期时间的 key)、allkeys-*(淘汰所有 key);
  • 按算法划分:lru (上次访问时间最老的)、lfu (最近访问次数最少得)、random (随机)、ttl(淘汰剩余过期时间最短的);
  • 特殊策略:noeviction(默认),内存不足时新增操作报错。

六、命令与操作类

6.1、怎样测试 Redis 服务器的连通性

执行 ping 命令,服务器返回 PONG 表示连通正常。

6.2、如何设置 key 的过期时间

方式 1:set key value EX seconds(设置值时直接指定秒级过期);

方式 2:expire key seconds(单独为已存在的 key 设置秒级过期);

毫秒级:PX milliseconds(set 选项)或 pexpire key milliseconds

6.3、为什么在生产环境上不应该使用**keys ***命令

时间复杂度 O (N),数据量较大时会阻塞 Redis 主进程,导致其他请求无法响应,引发生产故障

替代方案:使用 scan 命令渐进式遍历(每次 O (1),多次执行完成遍历)

6.4、Redis 的常用管理命令有哪些
  • dbsize:返回当前数据库 key 数量;
  • info:查看 Redis 服务器状态和统计信息;
  • monitor:实时监听所有请求;
  • shutdown:同步数据到磁盘并关闭服务;
  • config get/set parameter:获取 / 设置配置参数;
  • flushdb:删除当前数据库所有 key(慎用);
  • flushall:删除所有数据库的 key(慎用);
  • unlink key:异步删除 key(适合 bigkey,避免阻塞)
6.5、Redis 的 pipeline(流水线)是什么

**定义:**将多个 Redis 命令合并为一个请求发送,减少网络往返次数(RTT);

特点: 命令执行非原子性,仅批量传输,节省网络开销;

**用法:**通过客户端工具(如 redis-cli --pipe)或代码客户端批量提交命令

6.6、Redis 如何遍历 key

推荐使用 scan 命令:SCAN cursor [MATCH pattern] [COUNT count]

特点:

  • 游标从 0 开始,返回结果包含 "下次游标",游标为 0 时遍历结束;
  • 支持模糊匹配(MATCH)和指定每次返回数量(COUNT);
  • 对应结构专属命令:hscan(哈希)、sscan(集合)、zscan(有序集合)

七、其他问题

7.1、Redis 和 MySQL 如何保证双写一致性

**核心原则:**避免 "修改数据库后缓存未更新" 或 "缓存更新后数据库未修改"

解决方案:

方案 1:延时双删

删除缓存 → 更新数据库 → 延迟一段时间再次删除缓存;

方案 2:删除缓存重试

更新数据库 → 尝试删除缓存,失败则存入 MQ 重试,确保缓存删除成功

7.2、什么是 Redis 的 "bigkey" 问题?如何解决

**定义:**key 对应的 value 占用大量存储空间(如长字符串、包含大量元素的 hash/set)

**危害:**读写性能下降、集群分片数据倾斜、删除时阻塞 Redis

解决方案:

拆分 bigkey:将一个大 key 拆分为多个小 key 存储;

查找 bigkey:使用 redis-cli --bigkey 命令;

安全删除:用 unlink 命令异步删除,避免阻塞

7.3、如何实现 Redis 高可用

核心架构:主从复制 + 哨兵 + 集群

  • 主从复制:实现数据备份和读写分离;
  • 哨兵:自动完成主节点故障转移;
  • 集群:解决单节点存储容量限制,实现负载均衡和扩展性
7.4、什么是热 key 问题?如何解决

**定义:**某个 key 访问频率极高,集中冲击同一集群分片,导致该分片压力过大

解决方案:

热 key 所在分片增加从节点,分担读压力;

应用层对热 key 二次哈希,分散到多个分片存储;

单独为热 key 部署专属 Redis 集群;

应用层本地缓存热 key,减少 Redis 访问次数

7.5、如何理解 Redis 的事务?和 MySQL 的事务有啥区别
1、Redis 事务本质:

将多个命令放入 "事务队列",执行 EXEC 后批量执行,核心保证 "连续执行,不被其他命令插队";

2、与MySQL 事务的区别
  • 原子性:Redis 无回滚机制,单个命令失败不影响其他命令执行;
  • 一致性:不涉及约束校验,无中间非法状态保障;
  • 隔离性:单线程执行,无需隔离级别;
  • 持久性:依赖 Redis 持久化配置,与事务本身无关
3、相关命令:

MULTI(开启事务)

EXEC(执行事务)

DISCARD(放弃事务)

WATCH(监控 key,值变更则事务失效)

7.6、Redis 用到的网络通讯协议是怎样的
  • 协议名称:Redis Serialization Protocol(RESP),专为 Redis 设计的应用层协议;
  • 特点:纯文本协议,兼容性好、实现简单、可读性强。
7.7、Redis 如何实现 "查找附近的人"?

使用 GEO 地理信息类型:

存储:geoadd key 经度 维度 member 存入用户地理位置

查询:georadius key 经度 维度 距离 查找指定半径内的用户

7.8、Redis中的IO多路复用是怎么回事

**核心:**基于Linux提供的epoll机制完成

IO多路复用:就是用一个线程来管理多个socket(文件描述符),并按需激活线程

epoll内核维护了一个红黑树,来管理所有的socket,并且每个节点都关联了一个事件回调,当系统内核感知到网卡收到数据了,进一步判断这个数据是给哪个socket的,随之调用对应的回调,进一步唤醒线程来处理收到的数据。

7.9、Redis的key的过期删除策略

同时使用惰性过期和定性过期策略

**惰性过期:**在获取某个key时,Redis会检查一下,这个key如果设置了过期时间并且已经过期了,此时就会删除;

**定性过期:**每隔100ms就随机抽取一定数量的key来检查和删除

相关推荐
Neolnfra2 小时前
数据库提权实战指南
数据库·数据库安全
DarkAthena2 小时前
【GaussDB】合入原生PG的PR来修复CVE-2025-1094漏洞后产生的严重隐患
数据库·漏洞·gaussdb
予枫的编程笔记2 小时前
【Redis核心原理篇3】Redis 主从复制:数据同步的底层逻辑与实践
数据库·redis·缓存
pp起床2 小时前
【苍穹外卖】Day03 菜品管理
java·数据库·mybatis
关于不上作者榜就原神启动那件事2 小时前
多级缓存必要性
缓存
2301_803554522 小时前
Qt中connect()实现信号与槽连接这一核心机制
java·数据库·qt
海边的Kurisu3 小时前
苍穹外卖日记 | Day5 Redis
数据库·redis·缓存
冉冰学姐3 小时前
SSM药店管理系统fk5p7(程序+源码+数据库+调试部署+开发环境)带论文文档1万字以上,文末可获取,系统界面在最后面
数据库·计算机毕业设计、·ssm 框架应用·药店管理系统
予枫的编程笔记3 小时前
【Redis核心原理篇4】Redis 哨兵模式:自动故障转移的实现原理
数据库·redis·bootstrap