跳跃表是一种有序数据结构,它通过在每个节点中维持多个指向其他节点的指针,从而达到快速访问节点的目的。
Redis使用跳跃表作为有序集合键的底层实现之一,如果一个有序集合包含的元素数量比较多,又或者有序集合中的元素的成员是比较长的字符串时,Redis就会使用跳跃表作为有序集合键的底层实现。
Redis的跳跃表又redis.h/zskiplistNode和redis.h/zskiplist两个结构定义,其中zskiplistNode结构用于表示跳跃表节点,而zskiplist结构用于保存跳跃表节点的相关信息,比如节点的数量,以及指向表头节点和表尾节点的指针。
跳跃表节点的结构定义:
typedef struct zskiplistNode{
//后退指针
struct zskiplistNode *backward;
//分值
double score;
//成员对象
robj *obj;
//层
struct zskiplistLevel{
struct zskiplistNode *forward ;//前进指针
unsigned int span;//跨度
}level[];
}zskiplistNode
跳跃表结构定义:
typedef struct zskiplist{
//表示表头节点和表尾节点
struct zskiplistNode *header,*tail;
//表中节点的数量
unsigned long leagth;
//表中层数最大的节点的层数
//int level;
}zskiplist
header,tail指针分别指向跳跃表的表头和表尾节点,通过这两个指针,程序定位表头和表尾节点的复杂度为O(1)。
通过使用length属性来记录节点的数量,程序可以在O(1)复杂度内返回跳跃表的长度。
level属性则用在O(1)复杂度内获取跳跃表中层高最大的那个节点的层数量,注意表头节点的层高并不计算在内。