Redis 为什么快?
核心原因总览
内存存储 + 单线程模型 + 高效数据结构 + IO多路复用 + 简单协议
↓ ↓ ↓ ↓ ↓
无磁盘IO 无锁竞争 O(1)操作 高并发连接 低解析开销
一、全内存操作(最根本原因)
| 存储介质 | 访问延迟 |
|---|---|
| CPU 寄存器 | < 1ns |
| L1 Cache | ~1ns |
| 内存 (RAM) | ~100ns ✅ Redis |
| SSD | ~100μs |
| 机械硬盘 | ~10ms |
内存比磁盘快 10万倍,Redis 所有数据都在内存中,读写直接操作 RAM,无 IO 等待。
二、单线程模型(无锁竞争)
客户端1 ──┐
客户端2 ──┤──→ [ 事件队列 ] ──→ [ 单线程处理器 ] ──→ 顺序执行命令
客户端3 ──┘
为什么单线程反而快?
- ✅ 无线程切换开销:多线程的上下文切换本身消耗 CPU
- ✅ 无锁竞争:不需要 mutex/spinlock,省去加锁解锁开销
- ✅ CPU Cache 友好:单线程数据局部性好,Cache 命中率高
- ✅ Redis 瓶颈不在 CPU:瓶颈在网络 IO,多线程意义不大
⚠️ 注意:Redis 6.0+ 引入多线程处理网络 IO(读写数据),但命令执行仍是单线程。
三、IO 多路复用(高并发连接)
┌─────────────────────────┐
连接1 (可读) ──→ │ │
连接2 (可写) ──→ │ epoll / kqueue / select│──→ 单线程处理就绪事件
连接3 (等待) ──→ │ │
连接N ... ──→ └─────────────────────────┘
- 基于 epoll(Linux)实现事件驱动
- 一个线程同时监听成千上万个连接
- 只处理已就绪的 IO 事件,不阻塞等待
- 这就是 Redis 高并发的秘密
四、精心设计的数据结构
| 数据类型 | 底层结构 | 关键优化 |
|---|---|---|
| String | SDS(简单动态字符串) | 预分配内存,O(1) 获取长度 |
| List | quicklist(双向链表+ziplist) | 小数据用 ziplist 节省内存 |
| Hash | ziplist / hashtable | 小数据压缩存储 |
| Set | intset / hashtable | 纯整数用 intset,极省内存 |
| ZSet | ziplist / skiplist+hashtable | 跳表 O(logN) 有序操作 |
以 SDS 为例(对比 C 字符串):
c
// C 字符串获取长度:O(N) 遍历
strlen("hello") → 逐字符扫描
// SDS:O(1) 直接读 len 字段
struct SDS {
int len; // 直接返回,O(1) ✅
int free;
char buf[];
}
五、简单的通信协议(RESP)
// SET key value 的 RESP 协议格式
*3\r\n ← 3个参数
$3\r\nSET\r\n ← 命令
$3\r\nkey\r\n ← key
$5\r\nvalue\r\n ← value
- 协议纯文本,解析极简单
- 无 JSON/XML 序列化开销
- 批量命令(Pipeline)减少网络往返次数
六、Pipeline & 批量操作
# 不用 Pipeline:3次网络往返
Client → SET a 1 → Server
Client → SET b 2 → Server
Client → SET c 3 → Server
# 用 Pipeline:1次网络往返
Client → SET a 1 / SET b 2 / SET c 3 → Server(打包发送)
网络延迟(RTT)往往是性能瓶颈,Pipeline 直接消除多余的网络等待。
七、总结
┌────────────────────────────────────────────────┐
│ Redis 快的本质 │
├──────────────┬─────────────────────────────────┤
│ 内存存储 │ 消除磁盘 IO,延迟降低 10 万倍 │
│ 单线程 │ 消除锁竞争和上下文切换开销 │
│ IO 多路复用 │ 单线程支撑万级并发连接 │
│ 优秀数据结构 │ 针对场景优化,时间/空间最优 │
│ 简单协议 │ 解析快,支持 Pipeline 批处理 │
└──────────────┴─────────────────────────────────┘
最终结果:单机 QPS 可达 10万+ / 秒,延迟 < 1ms
一句话:Redis 把"能预先做的都做了,能省的都省了"发挥到了极致。