深入理解Redis基本数据结构(set集合,zset有序集合,跳表)——Redis深度历险笔记4

set就是一个特殊的hash

不知道hash是什么的请看上一章,hash类似java里的hashmap的数据结构。

set就类似java里的hashset。就是一种特殊的字典表。

set在进行add操作的时候进行去重工作,只存key,value都是null

zset面试官的最爱

zset在set的去重基础上,增加了一项排序功能。
还记得set的value都是null么,zset在value存score(分数),用这个分数来进行排序输出。

我们知道zset既有hash的功能,也有排序的功能。hash简单,还是可以用数组链表结构来实现,那么排序的功能该怎么办呢。必须有序排列吧,但是hash数组是随机的,才是好的hash数组。
那就说明。负责排序部分功能的,需要另一种数据结构出马。那就是跳表(skiplist)。

说明zset里面有2种数据结构,是个复合类型的数据。

跳表的基本结构

别忘了对象头

struct RedisObject {
	int4 type;//4bit,对象类型,那最多最多16种对象咯
	int4 encoding;//存储形式
	int24 lru;//Least Recently Used,最近最少使用信息
	int32 refcount;//暂未知,之后补上,todo
	void *ptr;//指向字典数据
}
struct zsl{
	zslnode* header;
	int maxLevel;//跳表最高层数
	map<String,zslnode*> ht;//hash结构,存储了链表的节点
}
struct zslnode{
	string value;//header里的value值是空的
	double score;//header里,score为Double.MIN_VALUE
	zslnode*[] forwards;
	zslnode* backword;
}

那么数据是存在跳表这个结构呢,还是存在hash这个结构呢?
由zsl的结构可知,是在跳表这个结构里的最后一层存储数据的,因为hash这个结构存储的是跳表节点的值。

如何构造跳表的索引

1、给定一个有序的链表。

2、选择连表中最大和最小的元素,然后从其他元素中按照一定算法(随机)随即选出一些元素,将这些元素组成有序链表。这个新的链表称为一层,原链表称为其下一层。

3、为刚选出的每个元素添加一个指针域,这个指针指向下一层中值同自己相等的元素。Top指针指向该层首元素

4、重复2、3步,直到不再能选择出除最大最小元素以外的元素。

跳表的查询

重点是查找最后一个比自己小的数,然后往下一层的索引去找。

跳表的插入,删除

如果节点已经存在,那么只是更新值。

插入的话,给这个节点计算一个层级。与ZSKIPLIST_P有关,就是不断轮询一个while,如果随机的数小于ZSKIPLIST_P的值,就将level+1,并继续随机,level初始值为1。

然后就将所有涉及到的索引都插入这个新的节点。

删除同理。

结语

跳表理解起来比较容易,但是真让写数据结构,还是得思考一下的。重点是理解,上面那几层,是索引,是新构造的节点了。就跟B+树的索引结构类似。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

rgbhi

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值