redis字符串源码分析sds

2021/5/4 19:25:37

本文主要是介绍redis字符串源码分析sds,对大家解决编程问题具有一定的参考价值,需要的程序猿们随着小编来一起学习吧!

前言

分析的为redis现在的最新版 6.2.3

源码链接:

sds.h: https://github.com/redis/redis/blob/unstable/src/sds.h

sds.c: https://github.com/redis/redis/blob/unstable/src/sds.c

sds结构体的定义

// sds的定义
typedef char *sds;

/* Note: sdshdr5 is never used, we just access the flags byte directly.
 * However is here to document the layout of type 5 SDS strings. */
// 不会被用到
struct __attribute__ ((__packed__)) sdshdr5 {
    unsigned char flags; /* 3 lsb of type, and 5 msb of string length */
    char buf[];
};
struct __attribute__ ((__packed__)) sdshdr8 {
    uint8_t len; // 字符串长度,buf已经用过的长度
    uint8_t alloc; // 字符串的总容量
    unsigned char flags; // 第三位保存类型标志
    char buf[];
};
struct __attribute__ ((__packed__)) sdshdr16 {
    uint16_t len; /* used */
    uint16_t alloc; /* excluding the header and null terminator */
    unsigned char flags; /* 3 lsb of type, 5 unused bits */
    char buf[];
};
struct __attribute__ ((__packed__)) sdshdr32 {
    uint32_t len; /* used */
    uint32_t alloc; /* excluding the header and null terminator */
    unsigned char flags; /* 3 lsb of type, 5 unused bits */
    char buf[];
};
struct __attribute__ ((__packed__)) sdshdr64 {
    uint64_t len; /* used */
    uint64_t alloc; /* excluding the header and null terminator */
    unsigned char flags; /* 3 lsb of type, 5 unused bits */
    char buf[];
};

我们看到sds的类型定义:

typedef char *sds;

所以这里为什么sds竟然等同于 char*?sds和传统的c语言字符串保持类型兼容,因此他们的定义是一样的,都是char*。这有些情况下,需要传入一个C语言字符串的地方,也确实可以传入一个sds。但是,sds和 char * 并不等同。sds是Binary Safe的,它可以存储任意二进制数据,不像C语言字符串那样以字符\0来标识字符串的结束,因此它必然有个长度字段。但是这个字段在哪?实际上还有一个header结构:

sds结构体从4.0开始就使用了5种header定义,节省内存的使用,但是不会用到sdshdr5。之所以有五种类型,就是为了节省内存:

  • sds5 对应1<<5 32
  • sds8 对应 1<<8 256
  • sds16 对应 1<<16 65536
  • sds32 对应 1<<32 2^32
  • sds64 对应 1<<16 2^64

一个sds字符串的完整结构,由在内存地址上前后相邻的两部分组成:

  • 一个header。通常包含字符串的长度(len), 最大容量(alloc)和flags。sdshdr5不同
  • 一个字符数组。这个字符数组的长度等于最大容量+1。真正有效的字符串数据,长度通常小于最大容量。
#define SDS_TYPE_5  0
#define SDS_TYPE_8  1
#define SDS_TYPE_16 2
#define SDS_TYPE_32 3
#define SDS_TYPE_64 4

sds内部结构解析

sds的数据结构,我们非常有必要非常仔细的去解析它

在这里插入图片描述

上图是一个内部的结构例子,画的很丑



这篇关于redis字符串源码分析sds的文章就介绍到这儿,希望我们推荐的文章对大家有所帮助,也希望大家多多支持为之网!


扫一扫关注最新编程教程