难缠的面试八股文哈希冲突,这次通透了

简介: 哈喽,我是指北君。最近有个读者后台私信指北君,说最近面试被问到了如何解决哈希冲突的问题,他只回答了链地址法(HashMap中就用的这种方法),但是面试官说还有其他的方案,于是想让小北解答下,说实话,当时小北也不知道。。。

不过没关系,不懂就学啊,小北百度了一波后,解答完读者的疑问就记录成了这篇文章


一. 哈希表


在介绍hash冲突的时候,先简单介绍下哈希表,哈希表也叫散列表,是根据关键值Key(Key value)而直接进行访问的数据结构。也就是说,它通过把关键码值中的Key映射到表中一个位置来访问记录,以加快查找的速度。其中,映射的实现也叫做哈希函数,而存放记录的数组叫做哈希表,其如下图所示

50.jpg


而hash冲突,就是将key通过哈希函数f(key)得到的结果的作为地址去存放当前的值时,发现算出来的地址上已经有人先来了。这就是所谓的hash冲突,下面我们看看具体的解决方案吧。


二. 哈希冲突解决方法

1)链地址法

这种方法是大家最熟悉的,因为Java HashMap中使用的就是这种方法。这种方法的基本思想是将所有哈希地址为i的元素构成一个称为同义词链的单链表,并将单链表的头指针存在哈希表的第i个单元中,因而查找、插入和删除主要在同义词链中进行。链地址法适用于经常进行插入和删除的情况。

优点:

  1. 对于记录总数频繁可变的情况,处理的比较好(也就是避免了动态调整的开销)
  2. 由于记录存储在结点中,而结点是动态分配,不会造成内存的浪费,所以尤其适合那种记录本身尺寸(size)很大的情况,因为此时指针的开销可以忽略不计了

缺点:

  1. 由于使用指针,记录不容易进行序列化(serialize)操作
  2. 存储的记录是随机分布在内存中的,这样在查询记录时,相比结构紧凑的数据类型(比如数组),哈希表的跳转访问会带来额外的时间开销
  3. 如果所有的 key-value 对是可以提前预知,并之后不会发生变化时(即不允许插入和删除),可以人为创建一个不会产生冲突的完美哈希函数(perfect hash function),此时封闭散列的性能将远高于开放散列

2)  开放定址法

这种方法也称再散列法,其基本思想是:当关键字key的哈希地址 p=f(key) 出现冲突时,以p为key,在通过哈希函数f(p)产生新的哈希地址p1,如果p1仍然冲突,再以p1为key,产生另一个哈希地址p2,…,直到找出一个不冲突的哈希地址pi ,将相应元素存入其中。

优点:

  1. 记录更容易进行序列化操作
  2. 如果记录总数可以预知,则可以创建完美哈希函数,此时处理数据的效率是非常高的

缺点:

  1. 存储记录的数目不能超过桶数组的长度,如果超过就需要扩容,而扩容会导致某次操作的时间成本飙升
  2. 由于记录是存放在桶数组中的,而桶数组必然存在空槽,所以当记录本身大小很大或者记录总数很大时,会导致明显的内存浪费

3) 再哈希法

这种方法是同时构造多个不同的哈希函数,当第一个哈希函数冲突后,我们使用第二个哈希函数,直到冲突不再产生。这种方法不易产生聚集,但增加了计算时间。

4)建立公共溢出区

这种方法的基本思想是:将哈希表分为基本表和溢出表两部分,凡是和基本表发生冲突的元素,一律填入溢出表。


三.  小结

好了,今天小北介绍了哈希冲突的解决方法,这个在面试中是会被经常问到的,所以大家需要重点关注下。

我是指北君,操千曲而后晓声,观千剑而后识器。感谢各位人才的:点赞、收藏和评论,我们下期更精彩!

相关文章
|
5月前
|
Java 调度 Windows
JAVA面试八股文之多线程基础知识
JAVA面试八股文之多线程基础知识
|
12月前
|
前端开发
2023Web前端开发八股文&面试题(万字系列)——这篇就够了!
2023Web前端开发八股文&面试题(万字系列)——这篇就够了!
1245 2
|
12月前
|
消息中间件 人工智能 Java
面试了一个前阿里P7,Java八股文与架构核心知识简直背得炉火纯青
前几天,跟个老朋友吃饭,他最近想跳槽去大厂,觉得压力很大,问我能不能分享些所谓的经验套路。 每次有这类请求,都觉得有些有趣,不知道你发现没有大家身边真的有很多人不知道怎么面试,也不知道怎么准备面试,哪怕是一些工龄比较长的“老开发”: 有的人明知道有些问题肯定会被问,面试前还不好好准备,结果要么回答得模棱两可,要么答非所问; 有的人则是不知道怎么包装自己的项目经历,结果明明还不错的项目却看上去平平无奇,过后就被面试官忘了; 更有甚者,简历写得花里胡哨,结果一问三不知,简历和经历完全对不上。
185 0
|
2月前
|
NoSQL Java 数据库
2022年整理最详细的java面试题、掌握这一套八股文、面试基础不成问题[吐血整理、纯手撸]
这篇文章是一份详尽的Java面试题总结,涵盖了从面向对象基础到分布式系统设计的多个知识点,适合用来准备Java技术面试。
2022年整理最详细的java面试题、掌握这一套八股文、面试基础不成问题[吐血整理、纯手撸]
|
4月前
|
存储 缓存 NoSQL
Redis八股文(大厂面试真题)
Redis八股文(大厂面试真题)
155 1
Redis八股文(大厂面试真题)
|
3月前
|
存储 缓存 前端开发
Java八股文面试之多线程篇
Java八股文面试之多线程篇
80 0
Java八股文面试之多线程篇
|
5月前
|
Java
Java面试挂在线程创建后续,不要再被八股文误导了!创建线程的方式只有1种
Java面试挂在线程创建后续,不要再被八股文误导了!创建线程的方式只有1种
46 1
|
5月前
|
消息中间件 Dubbo Java
24年国内头条最牛的Java面试八股文1000集,不接受反驳!
年后这个时间段, 找工作面试不要停!! 很多朋友据我了解,技术水平和工作经验都很不错,但是面试频频败北。 大家复盘下来发现问题不严重,但是很普遍,10个人里面8个都存在,那就是面试前不做准备。 技巧和避坑先不论,面试题型就不熟悉,没有系统过下大厂真题和必问项目,真正对线上面试官时被打的措手不及。 想要从容应对,就要提前建立把握和自信,这不但来自自身的技术能力水平,更来源于对面试时将要发生的各种情况有预判,做到心中有数。 这里整理了一套跳槽涨薪大厂Java知识点解析及面试题解析,涵盖20个技术栈的大厂面试题及详解文档,各大厂技术重点、面试难点、进阶要点,帮助大家“临阵磨枪”,如有需要的
|
5月前
|
消息中间件 人工智能 Java
面试了一个前阿里P7,Java八股文与架构核心知识简直背得炉火纯青
前几天,跟个老朋友吃饭,他最近想跳槽去大厂,觉得压力很大,问我能不能分享些所谓的经验套路。 每次有这类请求,都觉得有些有趣,不知道你发现没有大家身边真的有很多人不知道怎么面试,也不知道怎么准备面试,哪怕是一些工龄比较长的“老开发”: 有的人明知道有些问题肯定会被问,面试前还不好好准备,结果要么回答得模棱两可,要么答非所问; 有的人则是不知道怎么包装自己的项目经历,结果明明还不错的项目却看上去平平无奇,过后就被面试官忘了; 更有甚者,简历写得花里胡哨,结果一问三不知,简历和经历完全对不上。
|
5月前
|
Java 数据库连接 数据库
【万字长文】Java面试八股文:深入剖析常见问题与解答
【万字长文】Java面试八股文:深入剖析常见问题与解答
1059 0