Redis的数据结构-string

231 阅读2分钟

string是最基础的数据结构,其底层实现为简单动态字符串(Simple Dynamic String,SDS) 其结构,分为三部分

image.png

len存储buf的已用长度 alloc存储buf实际分配长度 buf就是我们写入的value内容,为了标示结束,会自动在最后加上\0,多占据1字节空间

因为 Redis 的数据类型有很多,而且,不同数据类型都有些相同的元数据要记录(比如最后一次访问的时间、被引用的次数等),所以,Redis 会用一个 RedisObject 结构体来统一记录这些元数据,同时指向实际数据

一个 RedisObject 包含了 8 字节的元数据和一个 8 字节指针,这个指针再进一步指向具体数据类型的实际数据所在,例如指向 String 类型的 SDS 结构所在的内存地址

同时,Redis 会使用一个全局哈希表保存所有键值对,哈希表的每一项是一个 dictEntry 的结构体,用来指向一个键值对。dictEntry 结构中有三个 8 字节的指针,分别指向 key、value 以及下一个 dictEntry,三个指针共 24 字节,Redis 使用的内存分配库 jemalloc 在分配内存时,会根据我们申请的字节数 N,找一个比 N 大,但是最接近 N 的 2 的幂次数作为分配的空间,这样可以减少频繁分配的次数,因此,一个dictEntry 实际会占用32字节。

image.png

综上,一个redis中存储一个string类型的值,我们不考虑存储的value自身的大小,光这些额外开支,就需要占用49字节,实际使用的时候,根据我们value的长度不同,还会有不同的空间因为jemalloc 的分配策略被浪费

启示:string数据类型不适合存储极大量的key,当key的量很大的时候,string数据类型的额外空间开支会很大