redis使用skiplist跳表的原因解析

 更新时间:2022年10月13日 10:59:07   作者:bitcarmanlee  
经常会有人问这个问题,redis中为什么要使用跳表?这个问题,redis作者已经给出过明确答案,今天通过本文再给大家讲解下这个问题,对redis skiplist跳表知识感兴趣的朋友一起看看吧

1.什么是skiplist跳表

跳表是一种特殊的链表,特殊的点在于其可以进行二分查找。普通的链表要查找元素只能挨个遍历链表中的所有元素,而跳表则利用了空间换时间的策略,在原来有序链表的基础上面增加了多级索引,然后利用类似二分查找的思路来快速实现查找功能。跳表可以支持快速的查找,插入,删除等操作,时间复杂度为O(logn),空间复杂度为O(n)。

2.随机层数的计算

跳表在节点插入时候,会随机出一个层数,依靠这个随机数操作构建的多层链表结构,能保证一个比较好的查找性能。这个随机层数不是一个普通的服从均匀分布的随机数,具体的计算逻辑如下

1.首先,每个节点肯定都有第1层指针(每个节点都在第1层链表里)。
2.如果一个节点有第i层(i>=1)指针(即节点已经在第1层到第i层链表中),那么它有第(i+1)层指针的概率为p。
3.节点最大的层数不允许超过一个最大值,记为MaxLevel。

伪代码如下

randomLevel()
    level := 1
    // random()返回一个[0...1)的随机数
    while random() < p and level < MaxLevel do
        level := level + 1
    return level

randomLevel逻辑中包含有两个参数,一个是概率p,一个是最大层数MaxLevel。在redis的实现中,这两个参数分别为

p = 1/4
MaxLevel = 32

该部分内容来自于如下文档:

skiplist的算法性能分析

关于跳表本身更详细的讲解可以参考上述文档。

3.redis为什么要使用跳表

经常会有人问这个问题,redis中为什么要使用跳表?

这个问题,redis作者已经给出过明确答案

  1. They are not very memory intensive. It’s up to you basically. Changing parameters about the probability of a node to have a given number of levels will make then less memory intensive than btrees.
  2. A sorted set is often target of many ZRANGE or ZREVRANGE operations, that is, traversing the skip list as a linked list. With this operation the cache locality of skip lists is at least as good as with other kind of balanced trees.
  3. They are simpler to implement, debug, and so forth. For instance thanks to the skip list simplicity I received a patch (already in Redis master) with augmented skip lists implementing ZRANK in O(log(N)). It required little changes to the code.

按照我自己的理解,稍微翻译一下就是
1.跳表不是非常吃内存,并且基本是取决于你自己。你可以通过改变参数p(第二部分中提到的),从而达到比btree消耗更少内存的目的。

2.redis中的zset结构经常会使用ZRANGE或者ZREVRANGE这种操作,这个时候遍历跳表就相当于遍历一个普通的链表。这种情况下,跳表的表现跟btree一样优秀。

3.很多人认为这一点是最重要的原因。跳表实现起来更容易,只需要一点点代码就能达到效果,修改起来也很方便。

到此这篇关于redis为什么要使用skiplist跳表的文章就介绍到这了,更多相关redis skiplist跳表内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • 使用高斯Redis实现二级索引的方法

    使用高斯Redis实现二级索引的方法

    本文介绍了如何通过高斯Redis搭建二级索引,二级索引在电商、图(hexastore)、游戏等领域具有广泛的应用场景,高斯redis现网亦有很多类似应用,需要的朋友跟随小编一起看看吧
    2022-07-07
  • Redis高可用之持久化

    Redis高可用之持久化

    在web服务器中,高可用是指服务器可以正常访问的时间,衡量的标准是在多长时间内可以提供正常服务(99.9%、99.99%、99.999%等等),Redis中,实现高可用的技术主要包括持久化、主从复制、哨兵和cluster集群,感兴趣的同学可以阅读本文
    2023-04-04
  • Redis下载部署并加入idea应用的小结

    Redis下载部署并加入idea应用的小结

    这篇文章主要介绍了Redis下载部署并加入idea应用,需要的朋友可以参考下
    2022-10-10
  • redis计数器与数量控制的实现

    redis计数器与数量控制的实现

    使用Redis计数器可以轻松地解决数量控制的问题,同时还能有效地提高应用的性能,本文主要介绍了redis计数器与数量控制的实现,具有一定的参考价值,感兴趣的可以了解一下
    2023-12-12
  • Redis慢查询的具体使用

    Redis慢查询的具体使用

    慢查询顾名思义就是比较慢的查询,但是究竟是哪里慢呢?本文详细的介绍了Redis慢查询的具体使用,具有一定的参考价值,感兴趣的可以了解一下
    2023-06-06
  • Redis内存碎片处理实例详解

    Redis内存碎片处理实例详解

    内存碎片是redis服务中分配器分配存储对象内存的时产生的,下面这篇文章主要给大家介绍了关于Redis内存碎片处理的相关资料,文中通过实例代码介绍的非常详细,需要的朋友可以参考下
    2022-05-05
  • 浅谈Redis中bind的坑

    浅谈Redis中bind的坑

    本文主要介绍了浅谈Redis中bind的坑,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2023-07-07
  • Redis分布式可重入锁实现方案

    Redis分布式可重入锁实现方案

    在单进程环境下,要保证一个代码块的同步执行,直接用synchronized 关键字或ReetrantLock 即可,在分布式环境下,要保证多个节点的线程对代码块的同步访问,就必须要用到分布式锁方案,本文介绍一下基于 Redis实现的分布式锁方案,感兴趣的朋友一起看看吧
    2024-02-02
  • redis清空所有数据的三种方法

    redis清空所有数据的三种方法

    本文主要介绍了redis清空所有数据的三种方法,主要包括FLUSHALL,FLUSHDB,SCREPT FLUSH这三个指令,具有一定的参考价值,感兴趣的可以了解一下
    2023-09-09
  • muduo源码分析之TcpServer模块详细介绍

    muduo源码分析之TcpServer模块详细介绍

    这篇文章主要介绍了muduo源码分析之TcpServer模块,本文通过实例图文相结合给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2022-04-04

最新评论