什么是跳表
- zset结构体里面一个是跳表,一个哈希表
- 跳表是在链表基础上改进过来的,实现了一种「多层」的有序链表,这样的好处是能快读定位数据
如果我们要在链表中查找节点 4 这个元素,只能从头开始遍历链表,需要查找 4 次,而使用了跳表后,只需要查找 2 次就能定位到节点 4,因为可以在头节点直接从 L2 层级跳到节点 3,然后再往前遍历找到节点 4。
复杂度 O(logN)。
- 跳表使用了二分查找思想,对原来的有序单链表加一级索引。索引层有两个指针,一个指向下一个节点,一个down指针,可以使查找更快
-
通过建立索引的方式,对于数据量越大的有序链表,通过建立多级索引,查找效率提升会非常明显。
-
这种链表加多级索引的结构 就是 跳表。
时间复杂度 空间复杂度
在跳表查询时,每一级索引 最多需要遍历3个节点。
那么在跳表中查询数据的时间复杂度就是 每一层遍历的节点数乘以层数 ,因此跳表中查找的时间复杂度就是**O(logn). ** 与二分查找的时间复杂度相同。
- 空间:o(n)
为什么不用红黑树
- 区间查找效率高
- 跳表灵活,他可以通过改变抽取间隔,灵活的平衡空间复杂度和时间复杂度
- 跳表容易实现,代码简单
什么时候使用跳表
如果一个有序集合包含的元素数量比较多,又或者有序集合中元素的成员(member)是比较长的字符串时,Redis就会使用跳跃表来作为有序集合键的底层实现。
压缩列表 -- 为了节省内存而开发的连续内存块组成的
本质上是一个字节数组,包含任意多个节点,每个节点可以保存一个字节数组或者一个整数值。当有序集合或散列表的元素个数比较少,且元素都是短字符串时,Redis便使用压缩列表作为其底层数据存储结构
- 保存元素(member)数量小于128
- 每个元素(member)长度小于64字节
在数据量较少的时候,ziplist充分体现了它内存的优势,又不会影响整体的查询效率
- zlbytes:整个列表字节数
- zltail:尾节点到头节点的偏移量
- zllen:记录节点数量
- previous_entry_length:前一个节点的长度
- encoding:记录本节点的类型和长度属性
- content:内容