Redis内部数据结构总结(3)ziplist

来源:互联网 发布:手机淘宝在哪装修 编辑:程序博客网 时间:2024/06/07 14:50

redis对外的数据结构hash的底层是ziplist或者dict。

        ziplist是一个经过特殊编码的双向链表,其设计目的就是为了提高存储效率。ziplist可以用于存储字符串或整数,其中整数是按真正的二进制表示进行编码的,而不是编码成字符串序列。

        ziplist提高了存储效率,是内存紧缩的列表,多个数据在一起的连续空间,不擅长修改,在两端pop,push快。

        hash的底层是ziplist,当数据变的越来越多,会转为dict,每次插入filed和value,ziplist数据项+2。

        

redis.conf的配置

hash-max-ziplist-entries 512hash-max-ziplist-value 64


hash-max-ziplist-entries 512,表示当hash项(field,value)数>512即ziplist项>1024的时候转为dict

hash-max-ziplist-value 64,表示当hash中的value长度超过64的时候转为dict。


ziplist的内存结构




hash为什么要转为dict?

Ⅰ,ziplist的数据发生改动,会引发内存realloc,可能导致内存拷贝。

Ⅱ,ziplist里查找需要进行遍历,数据项过多会变慢。


注:

Q:用redis的hash和string哪个结构更省内存?

A:不一定,因为可以先将对象用protocol buffer等方式序列化为字节数组,然后存入redis的string中。而hash随着数据的增大或者value比较大的时候转为dict,存储效率会下降,不过hash在支持的操作命令上比序列化后再存入string的方式还是有优势的:它既支持多个field同时存取(hmset,hmget),也支持按照某个特定的field单独存取(hset,hget)。


总之,ziplist是一个表(list),但不是一个链表(linkedlist)。ziplist将表中每一项存放在前后连续的地址空间内,一个ziplist整体占用一大块内存。而普通的双向链表每一项都占用独立的一块内存,各项之间用指针连接,这样会带来大量内存碎片,而且指针也会占用额外内存。




0 0