一、Redis的有序集合为什么使用 跳表 而不是 B+ 树
实现简单,内存友好
跳表是基于链表 + 多级索引实现的,逻辑简单,代码量少,容易维护。
Redis 的数据大多放在内存中,不需要像 B+ 树那样考虑磁盘 IO 的分层读取。
范围查询更自然
跳表通过多级索引快速定位,然后像链表一样向后遍历,非常适合区间查找。
Redis 的 有序集合 (Sorted Set, zset) 正是基于 跳表 + 哈希表 实现的。
比如
ZRANGE score 100 200
,用跳表可以顺序扫,很高效。更新(插入/删除)更快
跳表的插入/删除只需要修改相邻节点指针,平均复杂度 O(log n),实现简单。
B+ 树插入/删除可能触发节点分裂/合并,代码复杂,开销更大。
内存访问更高效
跳表是链表结构,节点分布更灵活,避免了频繁的树旋转或分裂操作。
Redis 运行在内存,随机访问代价低,不需要像磁盘存储那样追求树的高扇出特性。
👉 总结:
Redis 选择跳表是因为它简单、高效、适合内存操作,且范围查询支持非常自然。
二、MySQL 为什么使用 B+ 树 而不是 跳表
磁盘 IO 优化
MySQL 数据量通常非常大,无法全部放入内存,必须依赖磁盘。
B+ 树的每个节点可以存放多个键值(扇出高),高度低(一般 3~4 层就能存下上亿数据)。
查找数据时,磁盘访问次数非常少,大幅减少 IO。
顺序遍历高效
B+ 树的叶子节点是 链表连接 的,天然支持范围查询。
在磁盘上,B+ 树叶子节点通常是连续存储的,顺序读比跳表的随机指针跳转更高效。
更新时的平衡性
B+ 树在插入/删除时通过分裂/合并保持平衡,保证了查询效率的稳定。
跳表在磁盘环境下不如 B+ 树稳定(随机访问磁盘比顺序访问代价大很多)。
更适合大数据量存储
跳表是链表结构,节点分散,磁盘存储会产生大量随机 IO。
B+ 树节点利用率高、层数少,非常适合海量数据存储。
👉 总结:
MySQL 选择 B+ 树是因为它能最大限度减少磁盘 IO,且支持高效的范围查询,非常适合大规模持久化存储。
三、总结对比表
特性 跳表 (Redis) B+ 树 (MySQL) 存储环境 内存 磁盘 实现复杂度 简单 复杂 查询复杂度 O(log n) O(log n) 范围查询 高效(链表顺序遍历) 高效(叶子链表 + 磁盘顺序读) 插入/删除 快速,指针调整即可 可能分裂/合并,开销大 内存/磁盘友好 内存友好,指针操作快 磁盘友好,减少 IO 应用场景 Redis 有序集合(zset) MySQL 索引(B+ 树索引)
✅ 一句话记忆:
Redis 用跳表 → 追求内存效率、插入删除简单、范围查询自然。
MySQL 用 B+ 树 → 追求磁盘效率、减少 IO、适合大数据量存储。