本博客将顺着自顶向下的思路梳理一下Redis的数据结构体系,从数据库到对象体系,再到底层数据结构。我将基于我的一个项目的代码来进行介绍:daredis。该项目中,使用Java实现了Redis中所有的数据结构,思想与Redis大致类似,各种变量的命名与Redis源码基本一致,只是将结构体换成了类来实现。

Redis数据库

Redis服务器在初始化时,会创建一个db数组,大小默认是16,即创建16个数据库。如下所示:

public class RedisServer {

    private static int dbNum = 16;
public static RedisDB[] db; public static void init(){
db = new RedisDB[dbNum];
} public static void initDB(int index){
db[index] = new RedisDB();
}
}

RedisDB类型包含一个字典,代码如下:

public class RedisDB {

    //数据库的键空间
Dict<SDS, RedisObject> dict; public RedisDB() {
this.dict = new Dict<>();
}
}

数据库RedisDB实际上包含一个Dict类型,即字典(Redis中尤为关键的底层数据结构),是一个键值对集合,键名是SDS字符串,键值是RedisObject。Dict是后面要讲的一种底层数据结构,在数据库体系中也是用到了Dict。

可以这样理解,Redis的所有对象体系都是挂在一个Dict字典下的。这也体现了Redis非关系型的特点。

Redis对象系统

继续向下探索,看一看数据库键值RedisObject是什么。RedisObject表示Redis中的对象。Redis包含五种对象,统称对象系统

  • RedisHash哈希对象
  • RedisList列表对象
  • RedisSet集合对象
  • RedisString字符串对象
  • RedisZSet有序集合对象

RedisObject包含一个类型字段type和一个编码字段encoding,以及一个底层数据结构的引用ptr。如下所示:

public abstract class RedisObject {
protected int type;
protected int encoding;
protected RedisObj ptr;
}

type的值由一个枚举类型来维护,表示上述五种类型中的某种类型,如下所示

public enum RedisType {
STRING(0),
LIST(1),
HASH(2),
SET(3),
ZSET(4);
private final int val;
RedisType(int VAL) {
this.val = VAL;
}
public int VAL(){
return val;
}
}

encoding同样由一个枚举类型来维护,表示ptr指向的数据结构的类型,如下所示

public enum RedisEnc {
RAW(0),
INT(1),
HT(2),
LINKEDLIST(3),
ZIPLIST(4),
INTSET(5),
SKIPLIST(6),
EMBSTR(7);
private final int val;
RedisEnc(int VAL) {
this.val = VAL;
}
public int VAL(){
return val;
}
}

RedisObject中的ptr引用的对象可以是多种类型。例如列表对象可由压缩列表ziplist或者双端链表linkedlist来编码。两种编码可以转换,当满足以下两个条件时,使用ziplist编码

  • 列表对象保存的所有字符串元素长度都小于64字节;
  • 列表对象保存的元素数量小于512个;

两个条件有一项不满足,会将压缩列表转化为双端链表。

其它Redis对象的数据结构编码切换方式也与之类似。

Redis底层数据结构

底层数据结构指的是ptr指向的对象的内部结构,在Redis中,包含6种底层数据结构:

  • SDS动态字符串
  • ziplist压缩列表
  • list链表
  • dict字典
  • skiplist跳跃表
  • intset整数集合

熟悉Redis的同学来说,这些都是耳熟能详的数据结构,就不一一去介绍源码了,项目daredis中都有具体实现。

之前写过一篇介绍跳跃表的博客,也可以看看:

【Redis】跳跃表原理分析与基本代码实现(java)

对象系统与各种底层数据结构映射关系如下:

【Redis】内部数据结构自顶向下梳理的更多相关文章

  1. [转]Redis内部数据结构详解-sds

    本文是<Redis内部数据结构详解>系列的第二篇,讲述Redis中使用最多的一个基础数据结构:sds. 不管在哪门编程语言当中,字符串都几乎是使用最多的数据结构.sds正是在Redis中被 ...

  2. redis内部数据结构

    redis内部数据结构,是指redis在自身的构建中,基于这些特定的内部数据结构进行的. 简单动态字符串:Simple Dynamic String 双端链表 字典:Dictonary 跳跃表:ski ...

  3. Redis学习笔记-Redis内部数据结构

    Redis内部数据结构 Redis和其他key-value数据库的很大区别是它支持非字符串类型的value值.它支持的value值的类型如下: sds (simple dynamic string) ...

  4. 探索Redis设计与实现6:Redis内部数据结构详解——skiplist

    本文转自互联网 本系列文章将整理到我在GitHub上的<Java面试指南>仓库,更多精彩内容请到我的仓库里查看 https://github.com/h2pl/Java-Tutorial ...

  5. 探索Redis设计与实现7:Redis内部数据结构详解——intset

    本文转自互联网 本系列文章将整理到我在GitHub上的<Java面试指南>仓库,更多精彩内容请到我的仓库里查看 https://github.com/h2pl/Java-Tutorial ...

  6. 探索Redis设计与实现5:Redis内部数据结构详解——quicklist

    本文转自互联网 本系列文章将整理到我在GitHub上的<Java面试指南>仓库,更多精彩内容请到我的仓库里查看 https://github.com/h2pl/Java-Tutorial ...

  7. 探索Redis设计与实现4:Redis内部数据结构详解——ziplist

    本文转自互联网 本系列文章将整理到我在GitHub上的<Java面试指南>仓库,更多精彩内容请到我的仓库里查看 https://github.com/h2pl/Java-Tutorial ...

  8. 探索Redis设计与实现3:Redis内部数据结构详解——sds

    本文转自互联网 本系列文章将整理到我在GitHub上的<Java面试指南>仓库,更多精彩内容请到我的仓库里查看 https://github.com/h2pl/Java-Tutorial ...

  9. 探索Redis设计与实现2:Redis内部数据结构详解——dict

    本文转自互联网 本系列文章将整理到我在GitHub上的<Java面试指南>仓库,更多精彩内容请到我的仓库里查看 https://github.com/h2pl/Java-Tutorial ...

随机推荐

  1. DotNetty关键概念及简单示例(基于NET5)

    DotNetty关键概念及简单示例(基于NET5) 目录 DotNetty关键概念及简单示例(基于NET5) 1.DotNetty 设计的关键 1.1 核心组件 1.1.1 Channel 1.1.2 ...

  2. MySQL——一致性非锁定读(快照读)&MVCC

    MySQL--一致性非锁定读(快照读) MySQL数据库中读分为一致性非锁定读.一致性锁定读 一致性非锁定读(快照读),普通的SELECT,通过多版本并发控制(MVCC)实现. 一致性锁定读(当前读) ...

  3. day1(初始化项目结构)

    1.初始化项目结构  └─shiyanlou_project    │  .gitignore    │  README.en.md           # 英文    │  README.md    ...

  4. 基于gRPC的注册发现与负载均衡的原理和实战

    gRPC是一个现代的.高性能.开源的和语言无关的通用RPC框架,基于HTTP2协议设计,序列化使用PB(Protocol Buffer),PB是一种语言无关的高性能序列化框架,基于HTTP2+PB保证 ...

  5. PyQt程序执行时报错:AttributeError: 'winTest' object has no attribute 'setCentralWidget'的解决方法

    用QtDesigner设计了一个UI界面,保存在文件Ui_wintest.ui中,界面中使用了MainWindow窗口,窗口名字也叫MainWindow,用PyUIC将其转换成了 Ui_wintest ...

  6. JMeter断言/检查点

    断言就类似LoadRunner中的检查点.对上一个请求返回的信息,获取部分字符串.图片等做判断,确保返回的信息的准确性. 右键点击"HTTP请求" -> "添加&q ...

  7. Hadoop 中HDFS、MapReduce体系结构

    在网络环境方面,作为分布式系统,Hadoop基于TCP/IP进行节点间的通信和传输. 在数据传输方面,广泛应用HTTP实现. 在监控.通知方面,Hadoop等分布式大数据软件则广泛使用异步消息队列等机 ...

  8. 个人作业三——ATM管理系统

    一 作业信息 博客班级 https://edu.cnblogs.com/campus/ahgc/AHPU-se-JSJ18/ 作业要求 https://edu.cnblogs.com/campus/a ...

  9. 密码学系列之:明文攻击和Bletchley Park

    目录 简介 crib和明文攻击 布莱奇利公园(Bletchley Park) 简介 明文攻击就是指已经知道了部分明文和它对应的加密后的字段,从而可以推测出使用的加密手段或者密码本.明文攻击这个故事还要 ...

  10. sql注入之union注入

    联合查询注入利用的前提: 必须要有回显 联合查询过程: 判断是否存在注入点 判断是什么类型注入(字符型or数字型) 判断闭合方式 查询列数个数(order by) 5, 获得数据库名 获得表名 获得字 ...