10道不得不会的 Java容器 面试题

news2024/11/26 13:57:31

博主介绍: 🚀自媒体 JavaPub 独立维护人,全网粉丝15w+,csdn博客专家、java领域优质创作者,51ctoTOP10博主,知乎/掘金/华为云/阿里云/InfoQ等平台优质作者、专注于 Java、Go 技术领域和副业。🚀


最少必要面试题 ,获取《10万字301道Java经典面试题总结(附答案)》pdf,背题更方便,一文在手,面试我有

突击面试 | 突击面试 | 突击面试

我是JavaPub,专注于面试、副业,技术人的成长记录。

以下是 Java容器 面试题,相信大家都会有种及眼熟又陌生的感觉、看过可能在短暂的面试后又马上忘记了。JavaPub在这里整理这些容易忘记的重点知识及解答建议收藏,经常温习查阅

评论区见

文章目录

      • 1. 请说一下Java容器集合的分类,各自的继承结构
      • 2. Collection 和 Collections 有什么区别?
      • 3. List、Set、Map 之间的区别是什么?
      • 4. HashMap 和 Hashtable 有什么区别?
      • 5. 说一下 HashMap 的实现原理?
      • 6. 谈谈 ArrayList 和 LinkedList 的区别
      • 7. 谈谈ArrayList和Vector的区别
      • 8. 请谈一谈 Java 集合中的 fail-fast 和 fail-safe 机制
      • 9. HashMap是怎样确定key存放在数组的哪个位置的?JDK1.8
          • 9.1. 追问:为什么计算key的hash时要把hashCode的高16位与低16位进行异或?(变式:为什么不直接用key的hashCode)?
      • 10. 为什么要把链表转为红黑树,阈值为什么是8?
      • 拓展题. 为什么 HashMap 数组的长度是2的幂次方?

1. 请说一下Java容器集合的分类,各自的继承结构

Java 容器分为 Collection 和 Map 两大类,其下又有很多子类,如下所示:

Collection包括:List、ArrayList、LinkedList、Vector、Stack、Set、HashSet、LinkedHashSet、TreeSet

Map包括:HashMap、LinkedHashMap、TreeMap、ConcurrentHashMap、Hashtable

2. Collection 和 Collections 有什么区别?

Collection 是一个集合接口,它提供了对集合对象进行基本操作的通用接口方法,所有集合都是它的子类,比如 List、Set 等。

Collections 是一个包装类,包含了很多静态方法,不能被实例化,就像一个工具类,比如提供的排序方法:Collections. sort(list)。

3. List、Set、Map 之间的区别是什么?

List、Set、Map 的区别主要体现在两个方面:元素是否有序、是否允许元素重复。

4. HashMap 和 Hashtable 有什么区别?

  • HashMap 是非线程安全的,HashTable 是线程安全的。
  • HashMap 的键和值都允许有 null 值存在,而 HashTable 则不行。
  • 因为线程安全的问题,HashMap 效率比 HashTable 的要高。
  • Hashtable 是同步的,而 HashMap 不是。因此,HashMap 更适合于单线程环境,而 Hashtable 适合于多线程环境。
  • 一般现在 **不建议用 HashTable **,
    • 一方面是因为 HashTable 是遗留类,内部实现很多没优化和冗余。
    • 另外,即使在 多线程 环境下,现在也有同步的 ConcurrentHashMap 替代,没有必要因为是多线程而用 HashTable。

5. 说一下 HashMap 的实现原理?

HashMap 基于 Hash 算法实现的,我们通过 put(key,value)存储,get(key)来获取。当传入 key 时,HashMap 会根据
key. hashCode() 计算出 hash 值,根据 hash 值将 value 保存在 bucket 里。

当计算出的 hash 值相同时,我们称之为 hash 冲突,HashMap 的做法是用链表和红黑树存储相同 hash 值的 value。当 hash
冲突的个数比较少时,使用链表否则使用红黑树。

6. 谈谈 ArrayList 和 LinkedList 的区别

本质的区别来源于两者的底层实现:ArrayList的底层是数组,LinkedList的底层是双向链表。

数组拥有O(1)的查询效率,可以通过下标直接定位元素;链表在查询元素的时候只能通过遍历的方式查询,效率比数组低。

数组增删元素的效率比较低,通常要伴随拷贝数组的操作;链表增删元素的效率很高,只需要调整对应位置的指针即可。

以上是数组和链表的通俗对比,在日常的使用中,两者都能很好地在自己的适用场景发挥作用。

比如说我们常常用ArrayList代替数组,因为封装了许多易用的api,而且它内部实现了自动扩容机制,由于它内部维护了一个当前容量的指针size,直接往ArrayList中添加元素的时间复杂度是O(1)的,使用非常方便。

而LinkedList常常被用作Queue队列的实现类,由于底层是双向链表,能够轻松地提供先入先出的操作。

我觉得可以分两部分答,一个是数组与链表底层实现的不同,另一个是答ArrayList和LinkedList的实现细节。

7. 谈谈ArrayList和Vector的区别

两者的底层实现相似,关键的不同在于Vector的对外提供操作的方法都是用synchronized修饰的,也就是说Vector在并发环境下是线程安全的,而ArrayList在并发环境下可能会出现线程安全问题。

由于Vector的方法都是同步方法,执行起来会在同步上消耗一定的性能,所以在单线程环境下,Vector的性能是不如ArrayList的

除了线程安全这点本质区别外,还有一个实现上的小细节区别:ArrayList每次扩容的大小为原来的1.5倍;Vector可以指定扩容的大小,默认是原来大小的两倍。

可以顺带谈谈多线程环境下ArrayList的替代品,比如CopyOnWriteArrayList,但是要谈谈优缺点。

8. 请谈一谈 Java 集合中的 fail-fast 和 fail-safe 机制

fail-fast 是一种错误检测机制,Java 在适合单线程使用的集合容器中很好地实现了 fail-fast 机制,举一个简单的例子:在多线程并发环境下,A线程在通过迭代器遍历一个 ArrayList 集合,B线程同时对该集合进行增删元素操作,这个时候线程A就会抛出并发修改异常,中断正常执行的逻辑。

而fail-safe机制更像是一种对 fail-fast 机制的补充,它被广泛地实现在各种并发容器集合中。回头看上面的例子,如果线程A遍历的不是一个 ArrayList,而是一个 CopyOnWriteArrayList,则符合 fail-safe 机制,线程B可以同时对该集合的元素进行增删操作,线程A不会抛出任何异常。

要理解这两种机制的表象,我们得了解这两种机制背后的实现原理:

我们同样用 ArrayList 解释 fail-fast 背后的原理:首先 ArrayList 自身会维护一个 modCount 变量,每当进行增删元素等操作时,modCount 变量都会进行自增。当使用迭代器遍历 ArrayList 时,迭代器会新维护一个初始值等于 modCount 的 expectedModCount 变量,每次获取下一个元素的时候都会去检查 expectModCount 和 modCount 是否相等。在上面举的例子中,由于B线程增删元素会导致 modCount 自增,当A线程遍历元素时就会发现两个变量不等,从而抛出异常。

CopyOnWriteArrayList 所实现的 fail-safe 在上述情况下没有抛出异常,它的原理是:当使用迭代器遍历集合时,会基于原数组拷贝出一个新的数组(ArrayList的底层是数组),后续的遍历行为在新数组上进行。所以线程B同时进行增删操作不会影响到线程A的遍历行为。

9. HashMap是怎样确定key存放在数组的哪个位置的?JDK1.8

首先计算key的hash值,计算过程是:先得到key的hashCode(int类型,4字节),然后把hashCode的高16位与低16位进行异或,得到key的hash值。

接下来用key的hash值与数组长度减一的值进行按位与操作,得到key在数组中对应的下标。

9.1. 追问:为什么计算key的hash时要把hashCode的高16位与低16位进行异或?(变式:为什么不直接用key的hashCode)?

计算key在数组中的下标时,是通过hash值与数组长度减一的值进行按位与操作的。由于数组的长度通常不会超过2^16,所以hash值的高16位通常参与不了这个按位与操作。

为了让hashCode的高16位能够参与到按位与操作中,所以把hashCode的高16位与低16位进行异或操作,使得高16位的影响能够均匀稀释到低16位中,使得计算key位置的操作能够充分散列均匀。

10. 为什么要把链表转为红黑树,阈值为什么是8?

在极端情况下,比如说key的hashCode()返回的值不合理,或者多个密钥共享一个hashCode,很有可能会在同一个数组位置产生严重的哈希冲突。

这种情况下,如果我们仍然使用使用链表把多个冲突的元素串起来,这些元素的查询效率就会从O(1)下降为O(N)。为了能够在这种极端情况下仍保证较为高效的查询效率,HashMap选择把链表转换为红黑树,红黑树是一种常用的平衡二叉搜索树,添加,删除,查找元素等操作的时间复杂度均为O(logN)

至于阈值为什么是8,这是HashMap的作者根据概率论的知识得到的。当key的哈希码分布均匀时,数组同一个位置上的元素数量是成泊松分布的,同一个位置上出现8个元素的概率已经接近千分之一了,这侧面说明如果链表的长度达到了8,key的hashCode()肯定是出了大问题,这个时候需要红黑树来保证性能,所以选择8作为阈值。

追问:为什么红黑树转换回链表的阈值不是7而是6呢?

如果是7的话,那么链表和红黑树之间的切换范围值就太小了。如果我的链表长度不停地在7和8之间切换,那岂不是得来回变换形态?所以选择6是一种折中的考虑。

拓展题. 为什么 HashMap 数组的长度是2的幂次方?

因为这样能够提高根据 key 计算数组位置的效率。

HashMap 根据 key 计算数组位置的算法是:用 key 的 hash 值与数组长度减1的值进行按位与操作。

在我们正常人的思维中,获取数组的某个位置最直接的方法是对数组的长度取余数。但是如果被除数是2的幂次方,那么这个对数组长度取余的方法就等价于对数组长度减一的值进行按位与操作。

在计算机中,位运算的效率远高于取模运算,所以为了提高效率,把数组的长度设为2的幂次方。

所以一定要看一遍源码,相比于框架的源码,集合的源码简直太友好了。在笔试的时候可能还会考一些集合的使用,比如遍历,排序,比较等等,这些算是Java基础,用得多也就熟了。

低谷蓄力

最少必要面试题

10道不得不会的Java基础面试题

10道不得不会的Java并发基础面试题

10道不得不会的Java容器面试题

10道不得不会的JVM面试题

10道不得不会的MySQL基础面试题

10道不得不会的MyBatis面试题

10道不得不会的ElasticSearch面试题

10道不得不会的Spring面试题

10道不得不会的Redis面试题

10道不得不会的Kafka面试题

10道不得不会的Docker面试题

10道不得不会的Zookeeper面试题

10道不得不会的JavaEE面试题

10道不得不会的SpringBoot面试题

关注公众号,回复1024,获取Java学习路线思维导图、加入源码计划学习交流群

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/4270.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

FFmpeg内存IO模式

ffmpeg 支持从网络流 或者本地文件读取数据,然后拿去丢给解码器解码,但是有一种特殊情况,就是数据不是从网络来的,也不在本地文件里面,而是在某块内存里面的。 这时候 av_read_frame() 函数怎样才能从内存把 AVPacket…

TensorFlow的GPU使用相关设置整理

前言 TensorFlow是一个在机器学习和深度学习领域被广泛使用的开源软件库,用于各种感知和语言理解任务的机器学习。 默认情况下,TensorFlow 会映射进程可见的所有 GPU(取决于 CUDA_VISIBLE_DEVICES)的几乎全部内存。这是为了减少内…

国考省考行测:问题型材料主旨分析,有问题有对策,主旨是对策,有问题无对策,要合理引申对策

国考省考行测:问题型材料主旨分析,有问题有对策,主旨是对策,有问题无对策,要合理引申对策 2022找工作是学历、能力和运气的超强结合体! 公务员特招重点就是专业技能,附带行测和申论,而常规国考…

【Linux】Linux背景、环境的搭建以及用XShell实现远程登陆

目录Linux 背景Linux环境搭建Linux远程登陆Linux 背景 肯尼斯蓝汤普森最早用汇编语言创建了UNIX系统,后来与他的好“基友”丹尼斯里奇(C语言之父),他们两个一同用C语言重新写了UNIX系统,但是操作系统的使用是需要收费…

ActiveState Platform - November 2022

ActiveState Platform - November 2022 ActiveState平台定期更新新的、修补的和版本化的软件包和语言。 Python 3.10.7、3.9.14、3.8.14-解决了许多安全问题的点发布。 Python C库-ibxml 2.10.3、libxslt 1.1.37、libexpat 2.4.9、zlib 1.2.13、curl 7.85.0和sqlite3 3.39.4&am…

Python添加水印简简单单,三行代码教你批量添加

环境使用: Python 3.8Pycharm 如何配置pycharm里面的python解释器? 选择file(文件) >>> setting(设置) >>> Project(项目) >>> python interpreter(python解释器)点击齿轮, 选择add添加python安装路径 pycharm如何安装插件? 选择file(文件) …

使用Python PyQt5完成残缺棋盘覆盖仿真作业

摘要:本文内容是关于如何实现残缺棋盘覆盖仿真软件,算法课作业要求设计开发一个残缺棋盘覆盖仿真软件。使用”分治算法“求解问题,Python编程语言实现功能;使用PyQt5和Python热力图实现界面和仿真效果展示。 1 残缺棋盘覆盖仿真作…

[Linux打怪升级之路]-yun安装和gcc的使用

前言 作者:小蜗牛向前冲 名言:我可以接受失败,但我不能接受放弃 如果觉的博主的文章还不错的话,还请点赞,收藏,关注👀支持博主。如果发现有问题的地方欢迎❀大家在评论区指正。 本期学习目标&am…

Java:外包Java项目有什么好处?

Java已经成为众多解决方案的通用开发语言,包括web应用、游戏、软件开发等等。超过710万全球的Java程序员都在忙着为业界下一个最好的应用程序编码。 随着企业努力在当今的全球市场中保持竞争力,对Java项目外包的需求不断增加。 以下是你的企业通过外包Ja…

python基于PHP+MySQL的论坛管理系统

互联网给了我们一个互通互信的途径,但是如何能够更加高效的进行各种问题的分享和交流是很多人关心的问题,市面上比较知名的一些分享交流平台也很多,比如百度的贴吧,知乎等高质量内容分享平台,本系统是一个类似这样的论坛分享系统 随着互联网的发展人们分享和交流的分享也变的越…

leetcode刷题(128)——1575. 统计所有可行路径,动态规划解法

leetcode刷题(127)——1575. 统计所有可行路径,DFS解法 给你一个 互不相同 的整数数组,其中 locations[i] 表示第 i 个城市的位置。同时给你 start,finish 和 fuel 分别表示出发城市、目的地城市和你初始拥有的汽油总…

【CSS】CSS字体样式【CSS基础知识详解】

👨‍💻个人主页:花无缺 欢迎 点赞👍 收藏⭐ 留言📝 加关注✅! 本文由 花无缺 原创 本文章收录于专栏 【CSS】 【CSS专栏】已发布文章 📁【CSS基础认知】 📁【CSS选择器全解指南】 本文目录【CS…

物联网感知-光纤光栅传感器技术

一、光纤光栅传感技术 光纤光栅是利用光纤材料的光敏性,通过紫外光曝光的方法将入射光相干场图样写入纤芯,将周期性微扰作用于光纤纤芯,在纤芯内产生沿纤芯轴向的折射率周期性变化,从而形成永久性空间的相位光栅,其作用…

MySQL数据库的基本操作及存储引擎的使用

大家好呀!我是猿童学🐵,最近在学习Mysql数据库,给初学者分享一些知识,也是学习的总结,关注我将会不断地更新数据库知识,也欢迎大家指点一二🌹。 目录 一、常用的MySQL语句 二、创建…

使用ThinkMusic网站源码配合cpolar,发布本地音乐网站

1、前言 在我们的日常生活中,音乐已经成为不可或缺的要素之一,听几首喜欢的音乐,能让原本糟糕的心情变得好起来。虽然现在使用电脑或移动电子设备听歌都很方便,但难免受到诸多会员或VIP限制,难免让我们回想起音乐网站…

【JavaScript】常用内置对象——数组(Array)对象

文章目录什么是数组创建数组访问数组数组常用方法和属性投票传送门什么是数组 数组(Array)是最基本的集合类型,由于JavaScript是弱类型语言,因此JavaScript的数组和大多数语言的数组有所区别。在大多数语言中,当声明一…

ubuntu 20.04 qemu u-boot-2022.10 开发环境搭建

开发环境 ubuntu 20.04 VMware Workstation Pro 16 基于qemu(模拟器),vexpress-a9 平台 搭建 u-boot-2022.10 (当前最新版本) 准备工作 u-boot下载,下载最新稳定版本,当前为 u-boot-2022.10&#xff0…

代码随想录49——动态规划:121买卖股票的最佳时机、122买卖股票的最佳时机II

文章目录1.121买卖股票的最佳时机1.1.题目1.2.解答1.2.1.贪心算法1.2.2.动态规划2.122买卖股票的最佳时机II2.1.题目2.2.解答1.121买卖股票的最佳时机 参考:代码随想录,121买卖股票的最佳时机;力扣题目链接 1.1.题目 1.2.解答 1.2.1.贪心算…

第七节:类和对象【一】【java】

目录 🧾1. 面向对象的初步认知 1.1 什么是面向对象 1.2 面向对象与面向过程 📕2. 类定义和使用 2.1 简单认识类 2.2 类的定义格式 2.3 课堂练习 🎒3. 类的实例化 3.1 什么是实例化 3.2 类和对象的说明 3.3练习 🧾1. 面…

Hbase2.4.11安装

Hbase2.4.11安装 文章目录Hbase2.4.11安装一、前期准备二、安装三、配置文件(一)添加环境变量(二)修改hbase配置文件1.修改hbase-env.sh 中内容2.在hbase-site.xml中添加以下内容3. 编辑regionservers四、分发文件到Hadoop2、Hadoop3中一、前期准备 hba…