集合框架面试

news2024/11/28 23:07:36

1.常见的集合有哪些

主要分为3种List、Map、Set

2.ArrayList和LinkedList有什么区别

  • 数据结构不同:ArrayList是基于数组实现的,LinkedList是双向链表实现
  • 使用场景不同:ArrayList更利于查找,LinkedList利于增删
  • 是否支持随机访问:ArrayList是基于数组,所以他可以根据下标进行查找,支持随机访问(实现RandmoAccess接口,做一个标志)。LinkedList是基于链表,所以它没有办法根据序号直接获取元素,不支持随机访问。
  • 内存空间不同:ArrayList是基于数组,是一块连续的内存空间,LinkedList 基于链表,内存空间不连续,它们在空间占用上一些额外的消耗。

3.ArrayList的扩容机制

ArrayList是基于数组的集合,数组的容量是定义的时候就确定了,在插入的时候就会去判断是否需要扩容,如果超出当前的容量+1,那么就会扩容,扩容是创建一个1.5倍的数组,然后把原来数组的值拷进去。

4.快速失败(fail-fast)和安全失败(fail-safe)了解吗?

  • 快速失败fail-fast 是java集合的一种错误检测机制。原理:迭代器在遍历时直接访问集合中的内容,并且在遍历过程中使用一个 变量。集合在被遍历
    期间如果内容发生变化,就会改变modCount的值。每当迭代器使用hashNext()/next()遍历下一个元素之前,都会检测modCount变量是否为expectedmodCount值,是的话就返回遍历;否则抛出异常,终止遍历。
  • 安全失败fail-safe:原理:由于迭代时是对原集合的拷贝进行遍历,所以在遍历过程中对原集合所作的修改并不能被迭代器检测到,所以不会触发Concurrent Modification Exception

5.有哪几种实现ArrayList线程安全的方法

  • 使用Vector代替ArrayList,但是不推荐
  • 使用Collections.SynchronizedList保证ArrayList,然后操作包装后的list
  • CopyOnWriterArrayList代替ArrayList
  • 使用ArrayList时候应用程序通过同步机制去控制ArrayList的读写。

6.CopyOnWriteArrayList了解多少

CopyOnWriteArrayList是线程安全的版本的ArrayList。它的名字叫写时复制,采用了读写分离的并发策略。CopyOnWriterArrayList容器允许并发读,读操作是无锁的,性能较高。至于写操作则首先将当前的容器复制一份,然后再副本上执行写操作,结束后再将原来容器的引用指向新容器。

7. Map中Hashmap的数据结构

jdk1.7之前是数组加链表,1.7之后就是数组加链表加红黑树。在这里插入图片描述
其中桶数组是用来存储数据,链表是用来解决冲突,红黑树是为了便于提高查询效率。

  • 数据元素通过映射关系,也就是散列函数,映射到桶数组对应的索引位置
  • 如果发生冲突,从冲突的位置拉一个链表,放入冲突的元素
  • 如果链表长度大于8并且 数组>=64,链表转为红黑树。
  • 如果红黑树节点小于6,转为链表。

8.说说红黑树的理解

红黑树本质上也是一种二叉树,为了保持平衡它增加了一下规则

  1. 每个节点要么是黑色,要么是红色。
  2. 根节点永远是黑色
  3. 所有的叶子节点是黑色
  4. 每个红色节点的两个子节点是黑色
  5. 从任一节点到其子树中每个叶子节点的路径都包含相同数量的黑色节点。
    在这里插入图片描述
    之所以不用二叉树,红黑树本身就是一种平衡的二叉树,插入,删除查找的最坏时间复杂的都是O(logn)避免了二叉树最坏的情况下的O(n)时间复杂度。

之所以不用平衡二叉树:平衡二叉树是比红黑树更加严格的平衡树,为了保持平衡,需要旋转的次数更多,也就是说平衡二叉树保持平衡的效率更低,所以平衡二叉树插入和删除的效率比红黑树要低。

9.红黑树怎么保持平衡

红黑树有两种保持平衡的方式:旋转和染色

10. HashMap的put流程

在这里插入图片描述

  1. 首先进行哈希值的扰动,获取一个新的哈希值
  2. 判断tab是否空位或者长度为0,如果是则进行扩容
  3. 进行哈希值的下标计算,如果对应的下标没有存放数据,则直接插入否则就覆盖。
  4. 判断ta【i】是否为树节点,否则向链表中插入数据,是则向树中插入节点。
  5. 如果链表插入节点,链表长度大于8,则转化为红黑树。
  6. 最后所有数据处理完成后,判断是否超过阈值,超过则进行扩容。

11.HashMap是如何查找数据的

在这里插入图片描述

  1. 使用扰动函数,获取新的哈希值。
  2. 计算数组下标,获取节点。
  3. 匹配当前节点key是否满足,是直接返回
  4. 否则当前节点是否为树节点,是遍历树
  5. 否则遍历链表

12.HashMap的哈希/扰动函数是怎么设计的?

HashMap的哈希函数是先拿到 key 的hashcode,是一个32位的int类型的数值,然后让hashcode的高16位和低16位进行异或操作。

static final int hash(Object key)
{ int h;
// key的hashCode和key的hashCode右移16位 异或运算
return (key == null) ? 0 : (h = key.hashCode()) ^ (h >>> 16);
}

13.为什么Hashmap的容量是2的倍数

  1. 为了方便哈希取值
  2. 在扩容的时候,利用扩容的大小也是2的倍数,将已经产生hash碰撞的元素完美的移植到新的table中。

如果初始化HashMap,传一个17的值newHashMap<>,它会怎么处理?

简单来说,如果传递的不是2的倍数,那么会自动向上寻找离得最近的2的倍数,17的2的进制倍数是32。

14.你还知道那些哈希函数的构造方法呢

Hashmap里面的构造方法叫做除留取余法
除此以为还有

  • 直接定址法:直接根据key来映射到对应的位置。例如123就放到下标为123的地方
  • 数字分析法:取key的某些数组(如十位,百位)作为映射的位置
  • 平方取中法:取key平方的中间几位作为映射的位置
  • 折叠法:将key分割为位数相同的几段,然后把它们叠加作为映射的位置

15.解决哈希冲突有那些方法

HashMap使用链表的原因就是为了处理哈希冲突,这种方法就是

  • 链地址法:在冲突的地方拉一个链表,将冲突的元素放进去。

除此之外的一些解决方法

  • 开放地址法:就是在冲突的地方接着寻找下一个,给冲突元素找个空位。(线性探查法、平方探查法)
  • 在哈希法:换种哈希函数进行计算,重新计算冲突地址
  • 建立公共溢出区:在建立一个数组,把冲突的元素放进去

16.jdk1.8对Hashmap做了哪些优化

  1. 数据结构优化为数组,加链表加红黑树
  2. 链表插入方式:链表的插入方式从头插法变为了尾插法(原因 :因为 1.7 头插法扩容时,头插法会使链表发生反转,多线程环境下会产生环)
  3. 扩容rehash:扩容的时候 1.7 需要对原数组中的元素进行重新 hash 定位在新数组的位置,1.8 采用更简单的判断逻辑,不需要重新通过哈希函数计算位置,新的位置不变或索引 + 新增容量大小。
  4. 扩容时机:在插入的时候,1.7前是先判断是否需要扩容,1.8是先进行插入,插入完成在进行判断是否需要扩容。
  5. 散列函数:1.7做4次位移和4次异或,1.8只做1次(做4次的话边际效用也不大,改为一次,提升效率)

17.如何自己实现一个HashMap

整体设计:

  • 散列函数:hashcode+除留余数法
  • 冲突解决法:链地址法
  • 扩容:节点重新hash获取位置

18.HashMap是线程安全的吗

HashMap不是线程安全的,可能会发生这些问题

  • 扩容死循环(jdk1.7之前):1.7时候使用的是头插法,在多线程情况下会导致环形链出现,形成死循环。1.8之后使用尾插法,扩容时候会保持原有的链表元素顺序,不会出现环形链问题。
  • 多线程put可能导致元素丢失:多线程同时执行put操作,如果计算出来的索引位置是一样的,那么会造成前一个key被后一个key覆盖,从而导致元素的丢失。
  • put和get并发,可能导致get为null

19.有什么办法能解决HashMap线程不安全的问题呢?

java中有hashTable,Collections.synchronizedMap以及ConcurrentHashMap可以实现线程安全

  • hashTable是直接在操作方法上加上synchronized关键字,锁住整个table数组,粒度比较大。
  • Collections.synchronized是使用Collections集合工具的内部类,通过传入Map封装出一个SynchronizedMap对象,内部定义了一个对象锁,方法内部通过对象锁实现
  • ConcurrenthashMap在1.7中使用分段锁实现,在jdk1.8中使用cas+Synchronized

20.能具体说一下ConcurrentHashmap的实现吗?

ConcurrentHashmap线程安全在jdk1.7版本是基于分段锁 实现,在jdk1.8是基于CAS+synchronized 实现。
在这里插入图片描述
CAS+synchronized
jdk1.8实现线程安全不是在数据结构上下功夫,它的数据结构和HashMap是一样的,数组+链表+红黑树。它实现线
程安全的关键点在于put流程。
在这里插入图片描述

21.讲讲LinkedHashMap怎么实现有序的

HashMap是无序的,想要实现有序可以使用LinkedHashMap或者TreeMap

LinkedHashMap维护了一个双向链表,有头尾节点,同时LinkedHashMap节点Entry内部除了继承HashMap的Node属性,还有before和agter用于标识前置节点和后置节点在这里插入图片描述

22.讲讲TreeMap是怎么实现有序的

TreeMap是按照Key的自然顺序或者Comprator的顺序进行排序,内部是通过红黑树来实现。所以要么key所属的类实现Comprator接口,或者自定义一个Comprator的接口比较器,传给TreeMap
进行比较。
在这里插入图片描述

23.讲讲HashSet的底层实现?

HashSet的底层就是基于HashMap实现的,除了clone()、writeObject()、readObject是hashSet自己实现的外,其他都是调用hashmap方法进行实现的

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

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

相关文章

92.乐理基础-记号篇-演奏记号(三)刮奏、琶音

内容参考于&#xff1a;三分钟音乐社 上一个内容&#xff1a;91.乐理基础-记号篇-演奏记号&#xff08;二&#xff09;保持音、滑音-CSDN博客 下图红框里是之前的内容&#xff1a; 刮奏&#xff1a;它是滑音操作层面上的说法&#xff0c;可以把滑音理解成它是一种效果&#x…

kibana查看和展示es数据

本文来说下使用kibana查看和展示es数据 文章目录 数据准备查询所有文档示例kibana查看和展示es数据 数据准备 可以使用es的命令或者java程序来往&#xff0c;es进行新增数据 查询所有文档示例 在 apifox 中&#xff0c;向 ES 服务器发 GET请求 &#xff1a;http://localhost:92…

Live800:满足客户的情感需求:提升客户服务的新维度

在当前的商业环境中&#xff0c;提供优质的产品或服务已不再足够。消费者现在更关注他们与品牌的关系&#xff0c;以及品牌如何满足他们的情感需求。这就要求企业在提供客户服务时&#xff0c;不仅要解决客户的实际问题&#xff0c;也要关注和满足客户的情感需求。今天将探讨如…

深度强化学习Task1:马尔可夫过程、DQN算法回顾

本篇博客是本人参加Datawhale组队学习第一次任务的笔记 【教程地址】https://github.com/datawhalechina/joyrl-book 【强化学习库JoyRL】https://github.com/datawhalechina/joyrl/tree/main 【JoyRL开发周报】 https://datawhale.feishu.cn/docx/OM8fdsNl0o5omoxB5nXcyzsInGe…

基于Web的航空航天数字博物馆推荐系统

介绍 项目背景&#xff1a; 航空航天数字博物馆推荐系统是一个基于Web开发的应用&#xff0c;旨在为用户提供一个全面的航空航天领域的数字博物馆体验。通过展品展示、分类筛选和个性化推荐等功能&#xff0c;用户可以更好地了解航空航天知识和文化&#xff0c;并丰富参观体验…

笔试面试题——继承和多态

&#x1f4d8;北尘_&#xff1a;个人主页 &#x1f30e;个人专栏:《Linux操作系统》《经典算法试题 》《C》 《数据结构与算法》 ☀️走在路上&#xff0c;不忘来时的初心 文章目录 一、什么是多态&#xff1f;二、什么是重载、重写(覆盖)、重定义(隐藏)&#xff1f;三、 inli…

Open CASCADE学习|显示模型

目录 1、编写代码 Viewer.h Viewer.cpp ViewerInteractor.h ViewerInteractor.cpp helloworld.cpp 2、配置 3、编译运行 1、编写代码 Viewer.h #pragma once ​ #ifdef _WIN32 #include <Windows.h> #endif ​ // Local includes #include "ViewerInteract…

奥伦德光电耦合器5G通信领域及其相关领域推荐

光电耦合器是以光为媒介传输电信号的一种电-光-电转换器件。由于该器件使用寿命长、工作温度范围宽&#xff0c;所以在过程控制、工业通信、家用电器、医疗设备、通信设备、计算机以及精密仪器等方面有着广泛应用在当前工艺技术持续发展与提升的过程中&#xff0c;其工作速度、…

测试的基本概念

1、什么是需求&#xff1f; 在企业中主要分为两类&#xff1a;用户需求和软件需求 用户需求&#xff1a;甲方的需求&#xff0c;或者终端用户使用产品时必须要完成的任务&#xff08;比较简略&#xff09;。 软件需求&#xff1a;或者叫功能需求&#xff0c;该需求会详细描述开…

力扣hot100 二叉树中的最大路径和 递归

Problem: 124. 二叉树中的最大路径和 文章目录 解题方法复杂度&#x1f496; Code 解题方法 &#x1f468;‍&#x1f3eb; 参考思路 复杂度 时间复杂度: O ( n ) O(n) O(n) 空间复杂度: O ( n ) O(n) O(n) &#x1f496; Code /*** Definition for a binary tree no…

odoo16 销售订单中数量与单价,手机录入不方便

odoo16 销售订单中数量与单价&#xff0c;手机录入不方便 在销售订单中&#xff0c;服装批发&#xff0c;数量与单价均是整数&#xff0c;系统默认的为保留两位小数的float类型&#xff0c;输入起来很不方便&#xff0c;如何修改 电脑版&#xff0c;输入时&#xff0c;自动选取…

每日一题——LeetCode1281.整数的各位积和之差

方法一 个人方法&#xff1a; 没啥好说的&#xff0c;循环取n的最后一位就行&#xff1a; var subtractProductAndSum function(n) {var mulSumn%10,addSumn%10nMath.floor(n/10)while(n/10>0){let numn%10mulSum*numaddSumnumnMath.floor(n/10)}return mulSum-addSum };…

JAVA方法及练习

目录 Java方法的定义以及调用 带返回值方法的定义和调用 方法的重载 方法大练习 练习1 练习2 练习3 练习4 Java方法的定义以及调用 方法练习package java方法;public class fangfa1 {public static void main(String[] args) {xuexi();}//定义一个方法public static vo…

vue3__Provide / Inject (依赖注入)和mixins

一、 Provide提供和Inject 注入 Provide提供 <script setup> import { provide } from vueprovide(/* 注入名 */ message, /* 值 */ hello!) </script> 例如父组件中提供方法 <template> <div class"home">dfhualsf<div><button…

CMD常用命令

打开CMD winR——>输入cmd——>回车 常用cmd命令&#xff1a; 1.盘符名称冒号 盘符切换 举例&#xff1a;D回车&#xff0c;表示切换到D盘 2.dir 查看当前路径下的内容&#xff08;比如&#xff0c;该路径是文件夹&#xff0c;那么该文件夹中的内容将被展示出来&am…

【OpenAI】自定义GPTs应用(GPT助手应用)及外部API接口请求

11月10日&#xff0c;OpenAI正式宣布向所有ChatGPT Plus用户开放GPTs功能 简而言之&#xff1a;GPT应用市场(简称GPTs, 全称GPT Store) Ps&#xff1a; 上图为首次进入时的页面&#xff0c;第一部分是自己创建的GPTs应用&#xff0c;下面是公开可以使用的GPTs应用 一、创建GPTs…

【JavaEEj进阶】 Spring实现留言板

文章目录 &#x1f38d;预期结果&#x1f340;前端代码&#x1f384;约定前后端交互接⼝&#x1f6a9;需求分析&#x1f6a9;接⼝定义 &#x1f333;实现服务器端代码&#x1f6a9;lombok &#x1f332;服务器代码实现&#x1f334;运⾏测试 &#x1f38d;预期结果 可以发布并…

Ubuntu使用手册

点击前往查看&#x1f517;我的博客文章目录 Ubuntu使用手册 本篇文章原文是我的Ubuntu使用手册&#xff0c;在我的GitHub博客上&#xff0c;现在位于CSDN整理备份一份手册&#xff0c;方便操作Ubuntu的时候自己查阅&#xff0c;也欢迎各位网友翻阅。 Ubuntu系统环境搭建&…

kubernetes 灰度发布设计方案

ㅤㅤㅤ ㅤㅤㅤ ㅤㅤㅤㅤㅤㅤㅤㅤㅤㅤㅤㅤㅤㅤㅤ&#xff08;生活有时会迫使我们弯曲&#xff0c;但在弯曲的轨迹上&#xff0c;我们也能找到属于自己的旅程。 即便离开了我钟爱的技术领域&#xff0c;我仍然在新的旋律中发现着人生的节奏。- 史蒂夫乔布斯&#xff09; ㅤㅤㅤ ㅤ…

Linux/Traceback

Enumeration nmap 使用nmap初步扫描发现只开放了22和80端口&#xff0c;端口详细扫描情况如下 先看看web是什么样子的&#xff0c;打开网站发现有一条留言&#xff0c;显示该站点已经被黑了&#xff0c; 并且留下了后门 查看源代码&#xff0c;可以看到下面的注释 <!--So…