当前课程知识点:数据结构(下) > 第九章 词典 > (c)散列:散列函数 > 09C-4 以蝉为师
我们知道在实际应用中
我们所处理的数据通常都具有一定的局部性
其中一种典型的现象是
数据序列中的数据项 大多是按某一步长单调变化
想想你在程序中常写的while或者for之类的循环
就应该不难理解这一点
如果数据序列的步长为S
我们来考察S与M的最大公因子 将其记作G
假设这就是散列表的地址空间 其长度为M
而你的数据序列呢 将从某一个位置开始
以S为间隔 逐次的转入下一项 以及再下一项
当然如果你的数据序列足够长
它就有可能会从另一端回到这个空间
并且继续以S为间隔 在散列地址空间中逐次访问下去
现在考察这个数据序列在散列地址空间中留下的足迹
这些足迹能够遍历整个散列表空间吗
如果能 那么这种散列方法就具有均匀性 反之就不具有
借助数论的知识不难知道
数据序列的足迹能够遍布整个散列表
当且仅当刚才这个最大公因子等于1
请注意 因为可能有不同的程序
而每个程序的每一次运行所对应的这个步长
必然未必相等
也就是说 这里的M
相对于几乎任何S最大公因子都只能是1
这意味着什么呢
意味着M应该是一个素数
很有意思的是 很多动物 包括一些昆虫都懂得这个道理
在这里我们再次向蝉学习 学习它的哲学
没错 蝉的哲学
昆虫学告诉我们 蝉有很多变种
每一个变种都有其固定的生命周期
比如有些蝉是13年 而有些却是17年
那么蝉是否有某一个子类寿命是14年15年甚至16年呢
据我所知 没有
为什么没有呢
不妨回到我们的散列表
实际上 每一只蝉的生命周期
都可以对应为一个散列表
蝉的寿命有多长 散列表也就有多长
所以有些种类的蝉所对应的散列表长度为13
有些对应于17
当然也可能是11等等这类的素数
我们知道在自然界蝉是弱势群体
它有很多天敌 无论是螳螂还是螳螂之后的那只黄雀
每一种天敌大致也有一个自己的生命周期
这就相当于我们这里的步长S
没经过S年 蝉的天敌都会更新一代
当然 蝉不能去改变弱肉强食的法则
它唯一能期望的 只能是 在同一年 不要遇到更多的天敌
相应的 反过来 所有的天敌都应该在每一年分布的更加均匀
这更有利于蝉作为一个物种得以在自然界延续下去
用数学的语言来说 如果蝉能够选择自己的生命周期
那么自然的就应该选择与天敌的生命周期保持最大公约数为1
而为了与更多的天敌在生命周期上保持这种关系
尽管蝉有不同的变种 但是在经过长时间的进化之后
每一个变种都会聪明的将其生命周期设定为素数
正像我们所看到的那样 取做17 13等等
-选课之前
--写在选课之前
--宣传片
-考核方式
--考核方式
-OJ系统说明
--关于OJ
--1-注册与登录
--2-界面与选课
--3-提交测试
-关于课程教材与讲义
--课程教材与讲义
-关于讨论区
--关于讨论区
-微信平台
--html
-PA晋级申请
--PA晋级
-(a)概述
--07A-1 纵览
--07A-5 接口
-(a)概述--作业
-(b1)BST:查找
-第七章 二叉搜索树--(b1)BST:查找
-(b2)BST:插入
-(b2)BST:插入--作业
-(b3)BST:删除
-第七章 二叉搜索树--(b3)BST:删除
-(c)平衡与等价
-(c)平衡与等价--作业
-(d1)AVL树:重平衡
-第七章 二叉搜索树--(d1)AVL树:重平衡
-(d2)AVL树:插入
-(d2)AVL树:插入--作业
-(d3)AVL树:删除
-(d3)AVL树:删除--作业
-(d4)AVL树:(3+4)-重构
-(d4)AVL树:(3+4)-重构--作业
-本章测验
--章节测验
-(a1)伸展树:逐层伸展
--习题
-(a2)伸展树:双层伸展
--习题
-(a3)伸展树:算法实现
--习题
-(b1)B-树:动机
--习题
-(b2)B-树:结构
--习题
-(b3)B-树:查找
--习题
-(b4)B-树: 插入
--习题
-(b5)B-树: 删除
--习题
-(xa1)红黑树:动机
--习题
-(xa2)红黑树:结构
--习题
-(xa3)红黑树:插入
--习题
-(xa4)红黑树:删除
-本章测验
--习题
-(b)散列:原理
--09B-3 数组
--09B-4 原理
--09B-5 散列
--09B-6 冲突
--习题
-(c)散列:散列函数
--习题
-(d1)散列:排解冲突(1)
--习题
-(d2)散列:排解冲突(2)
--习题
-(e)桶/计数排序
--习题
-本章测验
--本章测试
-(a1)需求与动机
--习题
-(a2)基本实现
--习题
-(b1)完全二叉堆:结构
--习题
-(b2)完全二叉堆:插入与上滤
--习题
-(b3)完全二叉堆:删除与下滤
--习题
-(b4)完全二叉堆:批量建堆
--习题
-(c)堆排序
--习题
-(xa1)左式堆:结构
--习题
-(xa2)左式堆:合并
--习题
-(xa3)左式堆:插入与删除
-本章测验
--本章测试
-(a)ADT
--习题
-(b1)串匹配
--习题
-(b2)蛮力匹配
--习题
-(c1)KMP算法:从记忆力到预知力
--习题
-(c2)KMP算法:查询表
--习题
-(c3)KMP算法:理解next[]表
--习题
-(c4)KMP算法:构造next[]表
--习题
-(c5)KMP算法:分摊分析
--习题
-(c6)KMP算法:再改进
-(d1)BM_BC算法:以终为始
-(d2)BM_BC算法:坏字符
-(d3)BM_BC算法:构造bc[]
-(d4)BM_BC算法:性能分析
-(e1)BM_GS算法:好后缀
-(e2)BM_GS算法:构造gs表
-(e3)BM_GS算法:综合性能
-(f1)Karp-Rabin算法:串即是数
-(f2)Karp-Rabin算法:散列
-本章测验
--本章测试
-(a1)快速排序:算法A
-- 12a1-5: 实例
--习题
-(a2)快速排序:性能分析
--习题
-(a4)快速排序:变种
-(b1)选取:众数
-(b3)选取:通用算法
--习题
-(c1) 希尔排序:Shell序列
--习题
-(c2)希尔排序:逆序对
-本章测验
--本章测试