Redis sds源码详解

20191222157701368251284.png

redisObject

在redis中任何一个结构都会包含redisObject这样一个结构头。

1
2
3
4
5
6
7
8
9
typedef struct redisObject {
unsigned type:4;
unsigned encoding:4;
unsigned lru:LRU_BITS; /* LRU time (relative to global lru_clock) or
* LFU data (least significant 8 bits frequency
* and most significant 16 bits access time). */
int refcount;
void *ptr;
} robj;

占用内存大小为16byte

sds结构

再来看sds的结构

基本结构为sdshdr

以sdshdr8为例

1
2
3
4
5
6
struct __attribute__ ((__packed__)) sdshdr8 {
uint8_t len; /* used */
uint8_t alloc; /* excluding the header and null terminator */
unsigned char flags; /* 3 lsb of type, 5 unused bits */
char buf[];
};

占用内存大小3byte

内存计算

redisObject:16byte

sdshdr8:3byte

\0:1byte

共计20byte,所以一个sds类型,未考虑存储内容的情况下已经使用20byte的存储空间。

一个字符串sds占用的总内存为:20byte+char[]

假设字符为“redis” 那么存储占用的总内存大小为 20byte+5byte为25byte

redis开辟空间为2的次方:2、4、8、16、32、64

为了能容纳一个完整的 embstr 对象,redis最少会分配 32 字节的空间,如果字符串再稍微长一点,那就是 64 字节的空间。如果总体超出了 64 字节,Redis 认为它是一个大字符串,不再使用 embstr 形式存储,而该用 raw 形式。

所以redis字符串从embstr类型转为raw的阈值为44

C语言

详见:https://www.runoob.com/cprogramming/c-data-types.html

类型 存储大小 值范围
char 1 字节 -128 到 127 或 0 到 255
unsigned char 1 字节 0 到 255
signed char 1 字节 -128 到 127
int 2 或 4 字节 -32,768 到 32,767 或 -2,147,483,648 到 2,147,483,647
unsigned int 2 或 4 字节 0 到 65,535 或 0 到 4,294,967,295
short 2 字节 -32,768 到 32,767
unsigned short 2 字节 0 到 65,535
long 4 字节 -2,147,483,648 到 2,147,483,647
unsigned long 4 字节 0 到 4,294,967,295
lemon wechat
欢迎大家关注我的订阅号 SeeMoonUp
写的不错?鼓励一下?不差钱?