一、课前思考两节我们讲了二分查找算法。当时我讲到,因为二分查找底层依赖的是数组随机访问的特性,所以只能用数组来实现。如果数据存储在链表中,就真的没法用二分查找算法了吗? 实际上,我们只需要对链表稍加改造,就可以支持类似“二分”的查找算法。我们把改造之后的数据结构叫作跳表(Skiplist),也就是今天要讲的内容。 跳表这种数据结构对你来说,可能会比较陌生,因为一般的数据结构和算法书籍里都不怎么会讲。但是它确实是一种各方面性能都比较优秀的动态数据结构,可以支持快速的插入、删除、查找操作, 二、如何理解跳表1、单链表2、怎么提高查询效率1、18个节点一级索引2、18个节点二级索引3、64个节点建立五级索引3、当链表的⻓度n⽐较⼤时三、用跳表查询到底有多快1、如果链表⾥有n个结点,会有多少级索引?2、复杂度推算过程3、M值为什么是34、基于单链表实现二分查找四、跳表是不是很浪费内存1、索引节点数是一个等比数列2、通过等⽐数列求和公式3、实际上,在软件开发中,我们不必太在意索引占⽤的额外空间五、高效的动态插入删除1、在跳表单链表中插⼊⼀个数据的时间复杂度2、在跳表中删除⼀个数据的时间复杂度六、跳表索引动态更新1、如果链表中结点多了,索引结点就相应地增加⼀些2、跳表是通过随机函数来维护前⾯提到的“平衡性”3、如何选择加⼊哪些索引层呢?七、解答开篇1、如果你去查看Redis的开发⼿册,就会发现Redis中的有序集合⽀持的核⼼操作主要有下⾯这⼏个1、插⼊⼀个数据;删除⼀个数据;查找⼀个数据;2、按照区间查找数据(⽐如查找值在[100, 356]之间的数据3、迭代输出有序序列。2、Redis之所以⽤跳表来实现有序集合,还有其他原因3、跳表也不能完全替代红⿊树跳表的实现还是稍微有点复杂的,我将Java实现的代码放到了GitHub中,你可以根据我刚刚的讲解,对照着代码仔细思考⼀下。你不⽤死记硬背代码,跳表的实现并不是我们这节的重点 八、内容小结今天我们讲了跳表这种数据结构。跳表使用空间换时间的设计思路,通过构建多级索引来提高查询的效率,实现了基于链表的“二分查找”。跳表是一种动态数据结构,支持快速的插入、删除、查找操作,时间复杂度都是O(logn)。 跳表的空间复杂度是O(n)。不过,跳表的实现非常灵活,可以通过改变索引构建策略,有效平衡执行效率和内存消耗。虽然跳表的代码实现并不简单,但是作为一种动态数据结构,比起红黑树来说, 九、课后思考在今天的内容中,对于跳表的时间复杂度分析,我分析了每两个结点提取一个结点作为索引的时间复杂度。如果每三个或者五个结点提取一个结点作为上级索引, 经典留言escray如果每三个或者五个节点提取一个节点作为上级索引,那么对应的查询数据时间复杂度,应该也还是 O(logn)。 假设每 5 个节点提取,那么最高一层有 5 个节点,而跳表高度为 log5n,每层最多需要查找 5 个节点,即 O(mlogn) 中的 m = 5,最终,时间复杂度为 O(logn)。 来源:https://www./content-1-566201.html |
|