Redis经典五大类型源码及底层实现

Redis · 2023-06-22 · 316 人浏览

Redis经典五大类型源码及底层实现

image-20230618172021032

面试常问的

Redis对象object.c

字符串t_string.c

列表t_list.c

字典t_hash.c

集合及有序集合t_set.c和t_zset.c

数据流t_stream.c


Redis基本数据结构(骨架)

简单动态字符串sds.c

整数集合intset.c

压缩列表ziplist.c

快速链表quicklist.c

listpack

字典dict.c


Redis数据库的实现

数据库的底层实现db.c

持久化rdb.c和aof.c


Redis服务端和客户端

事件驱动ae.c和ae_epoll.c

网络连接anet.c和networking.c

服务端程序server.c

客户端程序redis-cli.c


其他

主从复制replication.c

哨兵sentinel.c

集群cluster.c

其他数据结构,如hyperloglog.c、geo.c等

其他功能,如pub/sub、Lua脚本

源码分析

image-20230618204411067

Redis中每个对象都是一个redisObject结构

每个键值对都会有一个digtEntry(源码位置:dict.h)

重点:从dictEntry到RedisObjectZ

image-20230618204730166

image-20230618204820775

image-20230618205353912

image-20230618205419879

经典5大数据结构解析

image-20230618205959767

image-20230618210041506

image-20230618210137173

image-20230618210225494

//edis结构
//*redis6相关的底层模型和结构*string = sDs
*set = intset + hashtable
*zset = skipList + zipList
*list = quickList + zipList
*hash = hashtable + zipList
*
===================================
*
*redis7相关的底层模型和结构
*string = SDS
*set = intset + hashtable
*zset = skipList + listpack紧凑列表
*List = quicklist
*Hash = hashtable + Listpack紧凑列表
*/

image-20230618210452450

image-20230618211301939

image-20230618211422964

image-20230618211442760

image-20230618211709376

image-20230618211726990

debug 的开启

image-20230618220239961

image-20230618220308104

String数据结构介绍

image-20230618221847191

image-20230618221859735

image-20230618221937164

image-20230618221955005

image-20230618222005207

image-20230618222037992

SDS简单动态字符串

image-20230618224006370

Hash数据结构介绍

image-20230619152103531

redis6

image-20230619152503891

image-20230619152544644

hash-max-ziplist-entries:使用压缩列表保存时哈希集合中的最大元素个数。
hash-max-ziplist-value:使用压缩列表保存时哈希集合中单个元素的最大长度。

结论

1.哈希对象保存的键值对数量小于512个;
2.所有的键值对的健和值的字符串长度都小于等于64byte (一个英文字母一个字节)
时用ziplist,反之用hashtable
ziplist升级到hashtable可以,反过来降级不可以(一旦从压缩列表转为了哈希表,Hash类型就会一直用哈希表进行保存而不会再转回压缩列表了。在节省内存空间方面哈希表就没有压缩列表高效了。)

image-20230619153139133

源码分析

image-20230619153343773

hset命令解读

image-20230619153846201

ziplist.c

image-20230619154011453

image-20230619175321788

image-20230619183348321

image-20230619183425087

image-20230619183517693

image-20230619183810619

image-20230619184019621

image-20230619184029979

image-20230619184205930

image-20230619195032621

image-20230619184632079

ziplist为了节省内存,采用了紧凑的连续存储。
ziplist是一个双向链表,可以在时间复杂度为O(1)下从头部、尾部进行 pop或push。
新增或更新元素可能会出现连锁更新现象(致命缺点导致被listpack替换)。
不能保存过多的元素,否则查询效率就会降低,数量小和内容小的情况下可以使用。

redis7

image-20230619195207624

image-20230619195327461

image-20230619195511587

image-20230619201209663

image-20230619201222756

源码

image-20230619201411623

image-20230619201419259

image-20230619201439147

image-20230619201640827

明明有ziplist了,为什么出来一个listpack紧凑列表?

Ziplsit的连锁更新问题

image-20230619202217661

image-20230619202316383

image-20230619202335276

结论:listpack 是Redis 设计用来取代掉ziplist 的数据结构,它通过每个节点记录自己的长度且放在节点的尾部,来彻底解决掉了ziplist存在的连锁更新的问题

image-20230619202612973

image-20230619202620359

image-20230619202646594

image-20230619202811926

ziplist内存布局VS listpack内存布局

image-20230619202919538

image-20230619203010789

List数据结构介绍

image-20230619210842464

image-20230619211328209

image-20230619211347412

image-20230619211524524

image-20230619211827552

image-20230619211950715

image-20230619212004662

image-20230619212023451

image-20230619212408804

Set数据结构介绍

image-20230619212452189

image-20230619212614656

image-20230619212726431

ZSet数据结构介绍

image-20230619212836899

image-20230619212912409

image-20230619212949754

image-20230619213133766

image-20230619213007934

image-20230619213017111

image-20230619213153595

总结

image-20230619213323442

image-20230619213403447

image-20230619213421192

image-20230619213501736

skiplist跳表

跳表是可以实现二分查找的有序链表

skiplist是一种以空间换取时间的结构。

由于链表,无法进行二分查找,因此借鉴数据库索引的思想,提取出链表中关键节点(索引),先在关键节点上查找,再进入下层链表查找,提取多层关键节点,就形成了跳跃表

but

由于索引也要占据一定空间的,所以,索引添加的越多,空间占用的越多

总结来讲跳表=链表+多级索引

跳表时间+空间复杂度介绍

image-20230619214725797

image-20230619214742013

image-20230619214754004


image-20230619214927768

image-20230619214955194

image-20230619215036071

Redis

上一篇 : Redis的缓存过期淘汰策略

下一篇 : Redis为什么快?高性能设计之epoll和IO多路复用深度解析

状态 统计 图床 又拍云提供CDN加速和云存储 阿里云提供服务计算服务

Powered by Typecho • Theme Jasmine