Redis - 底层数据结构

本文深入探讨 Redis 的底层数据结构,包括简单动态字符串 (SDS) 的优点、空间预分配和惰性空间释放,压缩列表 (ZipList) 的优缺点和连锁更新,快表 (QuickList) 的设计,字典 (Dict) 的哈希表结构、哈希冲突解决和渐进式重新哈希,整数集合 (IntSet) 的升级机制,以及跳跃表 (ZSkipList) 结构。通过对这些数据结构的理解,可以更好地掌握 Redis 的内部工作原理。
摘要由CSDN通过智能技术生成

简介

Redis 的底层数据结构主要以下几种:

  • SDS(Simple Dynamic String, 简单动态字符串)
  • ZipList(压缩列表)
  • QuickList(快表)
  • Dict(字典)
  • IntSet(整数集合)
  • ZSkipList(跳跃表)

简单动态字符串

在 Redis 中,并不会直接使用 C 语言自带的字符串结构作为实际的存储结构,而只是将字符串作为字面量使用,大多数情况使用自定义的 SDS 来表示字符串。

SDS 主要用于储存 Redis 的默认字符串表示、AOF 模块中的 AOF 缓冲区、客户端状态输入缓冲区。它的定义如下:

struct sdshdr {
    int len;        // 记录 buf 数组中已使用字节的数量,等于 SDS 所保存的字符串的长度
    int alloc;      // 记录 buf 数组中未使用字节的数量
    char buf[];     // 字节数组,用于保存字符串
};

优点

相对于 C 语言的字符串实现,Redis 实现的 SDS 有以下优点:

  • 通过记录 len 属性,实现常数级时间复杂度获取字符串长度
  • 通过检查 len 属性,避免字符串在修改时出现缓冲区溢出的情况
  • 通过记录 len 属性和 alloc 属性,对于修改字符串实现了空间预分配和惰性空间释放
  • 实际存储的 buf 是一个字节数组,可以实现 SDS 安全操作二进制数据
  • SDS 仍然以 \0 作为字符串结尾的标识,这样可以重用 C 语言字符串的部分函数

空间预分配

当 SDS 修改时需要扩展空间大小,程序不仅会为 SDS 扩展修改所需的空间,还会为 SDS 分配额外的未使用空间。这额外空间一般是 len 的大小,最大不超过 1MB。

这样可以减少连续执行字符串增长操作所需的内存重分配次数。

惰性空间释放

当 SDS 修改时需要缩短空间大小,程序并不会立即将多出来的空间进行空间重分配,而是使用 alloc 属性将这些空间大小记录下来,以待后续使用。

而且 SDS 也提供手动释放未使用空间的方法,这样可以避免浪费内存。

压缩列表

ZipList 实际是由一系列特殊编码的连续内存块组成的顺序型数据结构,是 Hash 类型底层实现的一种方式。

结构

一个 ZipList 结构由 zlbyteszltailzllenentrieszlend 这些属性组成,这些属性顺序连接在一起组成了 ZipList:

zlbytes 用于记录 ZipList 占用的内存字节数,在对 ZipList 进行内存重分配或者计算 zlend 的位置时使用。

zltail 记录了 ZipList 表尾结点距离 ZipList 的起始地址有多少个字节,Redis 可以通过这个属性快速确定表尾结点的地址。

zllen 记录了 ZipList 包含的结点数量,当这个属性小于 UINT16_MAX(65535) 时,这个值就是 ZipList 包含的结点数量;这个属性大于 UINT16_MAX 时,则需要遍历整个 ZipList 才能计算得出结点数量。一个 ZipList 可以包含任意多个结点,每个结点可以保存一个字节数组或者一个整数值。

zlend 定义了特殊值 OxFF 用于标记 ZipList 的末端。

优点

ZipList 是一种节省内存的列表结构,对于普通的数组来说,其中每个元素占用的空间大小取决于最大的元素,而 ZipList 解决了这个问题。

因此,ZipList 在设计的时候,尽量让每个元素按照实际的内容大小存储&#

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值