数据结构之散列

散列方法以给定变元K(关键词)为自变量,通过某种函数关系h(K)直接计算出函数值,这个值被解释为存放以K为关键词之记录的存储单元的地址。查找时,用相同方法计算出与给定变元K对应之记录的存储地址A,进而到A所指的存储单元中取出要查之记录。
1:散列函数
⑴ 压缩法
压缩法是把关键词的二进制串分割成若干个子串,然后按某种方式把这些子串合并形成该关键词的地址。比如利用异或运算进行合并,h(THE)=10100 XOR 01000 XOR 00101=11001=25。尽管异或运算不用担心溢出问题,但因异或运算满足交换律,则由相同字母组成的单词具有相同的散列地址。
⑵ 除法散列函数
使用模M的余数h(K)=K mod M。
⑶ 乘法散列函数
给定一个实数θ,0<θ<1,则我们可按如下的方式给出一个散列函数:
h(K)=取下整(M(Kθmod1))。
⑷ 平方取中法
该方法首先将K平方,然后取K²的中间部分作为h(K)的值。
⑸ 抽取法
从关键词的二进制串中抽取几个分散的代码,然后合并这几个代码而形成一个地址。

2:冲突调节
⑴ 拉链法
对应于h的值域[0, M-1]中的每一个值保持一个链表,每一个链表中存放着一组其关键词互相冲突的记录,该组关键词是K1, K2, … , Kt,且h(K1)=h(K2)=…=h(Kt)。
这里写图片描述
代码参考地址:http://www.cnblogs.com/lizhanwu/p/4303410.html

上述方法的改进是只对M个记录和M个链接域提供存储空间。
改进方法的算法:

算法C(TABLE[],K,M) 对于给定的变元K,本算法检索M个结点的表。若K不在表中且表不满,则把K插入表中。表中的结点用TABLE[i]来表示,对于0≦i≦M,并且每个结点都处于两种不同的状态之一:或为空或已占用。已占用的结点TABLE[i]包含关键词域KEY[i]和链接域LINK[i]。
本算法使用了一个散列函数h(K),R是一个辅助变量,用于找到空的空间,R的变化范围是从M到1。TABLE[0]将永远为空。
C1.[散列] 置i=h(K)+1;
C2.[有链表吗?] 若TABLE[i]为空,检索失败,则转到步骤C6(将K插入到TABLE[i]处;否则TABLE[i]已占用,应沿着由结点TABLE[i]开始的链表进行查找);
C3.[比较] 若K=KEY[i],则本算法以成功告终;
C4.[查找下一个] 若LINK[i]≠Λ,则置i=LINK[i]并返回步骤C3;
C5.[找空结点] 此时LINK[i]=Λ,在表中找到空位置插入K。令R减1,进行此操作直到TABLE[R]为空。若R=0,则本算法以溢出告终,表中已经没有空结点了;否则置LINK[i]=R,i=R。
C6.[插入K] 标记TABLE[i]为已占用,置KEY[i]=K,LINK[i]=Λ,算法以插入K成功告终。 

开地址法:
完全废除链接,对于给定的包含M个项目的表(表中项目或空或已占用),按照固定的次序检索表中的项目,直至或找到一个关键词等于给定的变元K或者找到一个空位置(从而将包含K的记录插入此位置)。
不同的解决冲突的策略,可产生不同的被检查的位置序列,称为探查序列。探查表中空闲位置的探查序列如下:h(K), (h(K)+p(1))modM, … , (h(K)+p(i))modM, …。依据生成探查序列的规则不同,有如下探查方法:
⑵ 线性探查法
是一种最简单的开地址法。它使用如下循环探查序列:
h(K), h(K)+1, … , M-1, 0, 1, … , h(K)-1
线性探查法有一个明显的缺点,它容易使许多元素在散列表中连成一片,从而使探查的次数增加,影响查找效率。这种现象称为基本聚集。
⑶ 伪随机探查法
基本思想:建立一个伪随机发生器,当发生冲突时,就利用伪随机发生器计算出下一个探查的位置。一种简单的生成器如下:y0=h(key), yi+1=(yi+p)modM,其中y0为伪随机发生器的初值,M为散列表的长度,p为与M接近的素数。
⑷ 二次探查法
二次探查使用下列探查序列:
h(key), h1(key), h2(key), … , h2i-1(key), h2i(key), …
其中,h2i-1(key)=(h(key)+i²) mod M,
h2i(key)=(h(key)-i²) mod M
式中,M是表的大小,它应当是一个值为4k+3的素数,k是一个整数。
⑸ 双重散列法
设 hash(key,i)=(hash’(key)+i×hash”(key)) mod M,其中i=0,1,…,M-1,hash’,hash”均为辅助散列函数
双重试探法的首个探查位置为hash’(key),当产生碰撞之后,接下来的探查位置为(hash’(key)+hash”(key)) mod M,因此我们发现在双重试探法中,不仅初始探查位置依赖于关键字key,探查序列中的增量hash”(key)同样依赖于关键字key,因而整个散列表提供了m2种不同的探查序列。其中hash”(key)要与M互质。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
数据结构中,散列(Hashing)是一种将数据元素通过散列函数映射到存储位置的方散列函数将数据元素的关键字作为输入,并计算出一个对应的散列值,然后将该散列值转化为存储位置,将数据元素存储在对应的位置上。散列的目的是使得数据元素能够均匀地分布在存储位置上,以便快速地进行插入、查找和删除操作。 散列结构是一种特殊的数据存储结构,它通过散列函数将关键字映射到存储位置,实现了快速的查找操作。散列结构通常使用散列表(Hash Table)来存储数据元素,散列表是一个具有固定大小的数组,每个数组元素称为槽(Slot),每个槽可以存储一个或多个数据元素。 散列结构的特点是查找操作的平均时间复杂度为O(1),即不受数据规模的影响,可以快速地找到要查找的数据元素。然而,散列结构也存在一些问题,例如散列冲突(Hash Collision),即不同的关键字映射到同一个存储位置,这种情况下需要使用解决冲突的方,如链地址、开放地址等。 总结来说,散列数据结构中是一种用于快速查找数据元素的技术,它通过散列函数将关键字映射到存储位置,实现了快速的插入、查找和删除操作。散列结构使用散列表来存储数据元素,具有查找时间复杂度为O(1)的特点,但也需要解决散列冲突的问题。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值