Java进阶(Set)——面试时Set常见问题解读 结合源码分析

news2024/11/20 20:25:28

在这里插入图片描述

前言

List、Set、HashMap作为Java中常用的集合,需要深入认识其原理和特性。

本篇博客介绍常见的关于Java中Set集合的面试问题,结合源码分析题目背后的知识点。

关于List的博客文章如下:

  • Java进阶(List)——面试时List常见问题解读 & 结合源码分析

其他相关的Set的文章如下:

  • Java学数据结构(3)——树Tree & B树 & 红黑树 & Java标准库中的集合Set与映射Map & 使用多个映射Map的案例

目录

  • 前言
  • 引出
  • 1. 描述一下HashSet的底层原理?
    • 构造方法
    • add方法
  • 2. map.put方法,静态常量PRESENT
  • 3. map.remove key方法,PRESENT进行比较
  • 4. HashSet的去重原理?
  • 5. 如何选择HashSet 或 TreeSet?
  • 6. 如何得到一个线程安全的Set集合?
  • 总结

引出


1.特点:无序,去重,非线程安全;
2.底层:HashMap的Key值实现的;
3.map.put方法,静态常量PRESENT,新值替换旧值;
4.map.remove key方法,如果KEY不存在时,则返回的是null,如果KEY存在时,返回的就是e.value,即PRESENT,返回true成功,返回false不成功;
5.去重原理:先判断hash值,再通过==或者equals判断,整体如果返回true,则为重复元素;
6.无序的则采用HashSet ,有序的则采用TreeSet;
7.线程安全的set:Collections.synchronizedSet(new HashSet<>());

1. 描述一下HashSet的底层原理?

  1. HashSet的特点:无序,去重,非线程安全
  2. HashSet 底层是用HashMap的Key值实现的,也有上面的3大特征;

构造方法

无参和代参构造方法都会初始化这个HashMap

无参的构造方法,调用了HashMap方法

在这里插入图片描述

有参的构造方法也是,调用了HashMap方法

在这里插入图片描述

![外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上在这里插入图片描述

add方法

在这里插入图片描述

add方法中可以看出调用HashMap的put方法,key为放入元素,值为常量PRESENT

在这里插入图片描述

2. map.put方法,静态常量PRESENT

既然hashset基于hashmap实现,你说一下 hashset的add方法中,为什么要在map.put的val上放上一个Object类型的静态常量PRESENT?

在这里插入图片描述

HashSet底层调用了map的put方法,传入了存储的对象和PRESENT常量,那我们进入put方法继续查看

在这里插入图片描述

put方法内调用了putVal方法,PRESENT常量为形参value,继续进入查看

在这里插入图片描述

	if (e != null) { // existing mapping for key
        //把旧数据存储到oldValue
        V oldValue = e.value;
        //如果说存储的位置上已经有元素了
        if (!onlyIfAbsent || oldValue == null)
            //新元素会替代旧元素   新KEY替代KEY
            e.value = value;
        afterNodeAccess(e);
        //返回旧元素数据
        return oldValue;
    }
    ++modCount;
    if (++size > threshold)
        resize();
    afterNodeInsertion(evict);
    //如果说上面的if结构没有执行,那么就说明这个位置上没有元素,则新增成功,返回null
    return null;

在这里插入图片描述

在这里插入图片描述

public boolean add(E e) {
        //上面的方法返回值决定了HashSet的add方法到底返回true还是false
        return map.put(e, PRESENT)==null;
    }
  1. 此方法内部明确箭头标处的原理,value就是PRESENT,如果进入这个if结构,则说明这个位置上已经存在该key,则会用value替换之前的旧值,然后返回旧值oldValue,否则会返回null;
  2. 至此,我们可以看出此方法的返回值是PRESENT或者是null,如果为PRESENT则说明KEY已存在,则add方法就会返回false(此处元素put还是成功的,只是新值替换旧值),返回null则add返回true,此KEY不存在,代表存储新的KEY-VALUE;

3. map.remove key方法,PRESENT进行比较

既然hashset基于hashmap实现,你说一下 hashset的remove方法中,为什么要在map.remove key 完了之后要和PRESENT进行一个等值比较呢?

在这里插入图片描述

在这里插入图片描述

  1. 从HashMap的remove方法中可以看出,方法返回的是e.value或者null,与add方法中的原理一起联想,则会明白,如果KEY不存在时,则返回的是null,如果KEY存在时,返回的就是e.value,即PRESENT
  2. 所以在HashSet在判断此返回值==PRESENT,如果相等则返回true,说明此KEY是存在的,删除成功返回true,如果返回值是null,那么null=PRESENT则返回的肯定是false,那么代表此KEY不存在,删除自然不成功,返回false;

在这里插入图片描述

public V remove(Object key) {
        Node<K,V> e;
        //判断了一下,如果removeNode删除得到的是null,说明此KEY不存在,方法返回null
        return (e = removeNode(hash(key), key, null, false, true)) == null ?
            //否则返回e.value   就是 PRESENT
            null : e.value;
    }
public boolean remove(Object o) {
        //因为HashMap删除成功返回的是PRESENT , ==PRESENT 则结果为true 代表删除成功
    //否则返回的是null , 返回false  删除失败
        return map.remove(o)==PRESENT;
    }

4. HashSet的去重原理?

在这里插入图片描述

  1. HashMap中putVal方法中有这么一段代码判断,去重原理在于hashcode的判断和equals方法的判断
  2. 先判断hash值,再通过==或者equals判断,整体如果返回true,则为重复元素

5. 如何选择HashSet 或 TreeSet?

无序的则采用HashSet ,有序的则采用TreeSet

6. 如何得到一个线程安全的Set集合?

Set datas = Collections.synchronizedSet(new HashSet<>());

在这里插入图片描述


总结

1.特点:无序,去重,非线程安全;
2.底层:HashMap的Key值实现的;
3.map.put方法,静态常量PRESENT,新值替换旧值;
4.map.remove key方法,如果KEY不存在时,则返回的是null,如果KEY存在时,返回的就是e.value,即PRESENT,返回true成功,返回false不成功;
5.去重原理:先判断hash值,再通过==或者equals判断,整体如果返回true,则为重复元素;
6.无序的则采用HashSet ,有序的则采用TreeSet;
7.线程安全的set:Collections.synchronizedSet(new HashSet<>());

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

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

相关文章

ssm+vue的孩童收养信息管理(有报告)。Javaee项目,ssm vue前后端分离项目。

演示视频&#xff1a; ssmvue的孩童收养信息管理(有报告)。Javaee项目&#xff0c;ssm vue前后端分离项目。 项目介绍&#xff1a; 采用M&#xff08;model&#xff09;V&#xff08;view&#xff09;C&#xff08;controller&#xff09;三层体系结构&#xff0c;通过Spring …

FPGA时序分析与约束(9)——主时钟约束

一、时序约束 时序引擎能够正确分析4种时序路径的前提是&#xff0c;用户已经进行了正确的时序约束。时序约束本质上就是告知时序引擎一些进行时序分析所必要的信息&#xff0c;这些信息只能由用户主动告知&#xff0c;时序引擎对有些信息可以自动推断&#xff0c;但是推断得到…

文件正在使用,操作无法完成。windows查看占用文件的程序

查看占用 tasklist /m IDMShellExt64.dll 映像名称 PID 模块explorer.exe 7452 IDMShellExt64.dll杀死进程 taskkill /f /PID 7452 成功: 已终止 PID 为 7452 的进程。重启explorer explorer

建筑能源管理(7)——建筑节能诊断内容

1、节能诊断简介 1.1、节能诊断目的 建筑节能诊断是一种建筑节能的科学管理和服务方法&#xff0c;其主要内容是对建筑能源使用的效率、消耗水平和能源利用的经济性进行客观考察&#xff0c;对建筑能源利用状况进行定量分析&#xff0c;对建筑能源利用效率、消耗水平、能源经…

媒介易再进化,6.0国际版新老用户必看

时隔一年&#xff0c;媒介易平台又双叒叕更新版本了&#xff01;这一次&#xff0c;我们带来了全新的6.0国际版&#xff0c;为大家提供更优质、更便捷的服务。 自2019年以来&#xff0c;平台不断推陈出新&#xff0c;优化用户体验&#xff0c;媒介易团队以“内容更新、视觉提升…

Linux高级命令(扩展)

一、find命令 1、find命令作用 在Linux操作系统中&#xff0c;find命令主要用于进行文件的搜索。 2、基本语法 # find 搜索路径 [选项 选项的值] ... 选项说明&#xff1a; -name &#xff1a;根据文件的名称搜索文件&#xff0c;支持*通配符 -type &#xff1a;f代表普通文…

CleanMyMac2024永久免费版Mac系统磁盘清理工具

Cleanmymac对很多用户来说已经非常熟悉了&#xff0c;因为在网上如果你搜寻有关清理mac系统方面的软件时&#xff0c;占比非常多的会是cleanmymac的相关消息。许多刚从Windows系统转向Mac系统怀抱的用户&#xff0c;一开始难免不习惯&#xff0c;因为Mac系统没有像Windows一样的…

【Linux】Centos 8 服务器部署:阿里云域名注册、域名解析、个人网站 ICP 备案详细教程

目录 一、背景信息 二、操作步骤 &#xff08;1&#xff09;查询域名 &#xff08;2&#xff09;加入域名清单 &#xff08;3&#xff09;确认订单信息 &#xff08;4&#xff09;支付 &#xff08;5&#xff09;等待域名实名认证通过 三、域名注册成功 四、查看域名…

学会吃亏,也是善良

《六祖坛经》上说&#xff1a;一切福田&#xff0c;都离不开心地。 心田上播下善良的种子&#xff0c;总有一天&#xff0c;会开花结果。 所以&#xff0c;心地善良是一种福祉&#xff0c;是对生命最好的感恩与回报&#xff0c;心存善念&#xff0c;便是最好的修行&#xff01;…

C#学习相关系列之多线程---ConfigureAwait的用法

一、ConfigureAwait的作用 ConfigureAwait方法是Task类中的一个实例方法&#xff0c;它用于配置任务的运行上下文。运行上下文指的是任务在执行期间所处的环境&#xff0c;包括线程、同步上下文等。ConfigureAwait方法接受一个布尔值参数&#xff0c;用于决定是否捕获上下文。当…

SHCTF2023-校外赛道WP部分

SHCTF2023-校外赛道WP部分 前言&#xff1a;Web&#xff1a;MISC&#xff1a;[WEEK1]签到题&#xff1a;[WEEK1] 真的签到&#xff1a;[WEEK1]可爱的派蒙捏&#xff1a;[WEEK1]也许需要一些py:[WEEK1]Jaeger lover&#xff1a;[WEEK1]message&#xff1a;[WEEK2]远在天边近在眼…

JAVA中的垃圾回收器(3)----ZGC

一)ZGC介绍:ZGC停顿时间不超过了1ms&#xff0c;且不会随着堆的增加而增加 如果堆空间越来越大&#xff0c;那么垃圾回收的造成的STW的时间会呈现线性的增长 堆空间分页模型:小页面优先回收&#xff0c;大页面尽量不回收 ZGC本身只是支持三种页面&#xff0c;分别是小页面&…

frp-内网穿透部署-ubuntu22服务器-windows server-详细教程

文章目录 1.下载frp2.配置服务器2.1.配置frps.ini文件2.2.设置服务文件2.3.设置开机自启和服务操作2.4.后台验证2.5.服务器重启 3.配置本地window3.1.frpc配置3.2.添加开机计划启动3.3.控制台启动隐藏窗口 4.centos防火墙和端口3.1.开放端口3.2.查看端口 5.关闭进程5.1.杀死进程…

NSS刷题 js前端修改 os.path.join漏洞

打算刷一遍nssweb题&#xff08;任重道远&#xff09; 前面很简单 都是签到题 这里主要记录一下没想到的题目 [GDOUCTF 2023]hate eat snake 这里 是对js的处理 有弹窗 说明可能存在 alert 我们去看看js 这里进行了判断 如果 getScore>-0x1e9* 我们结合上面 我觉得是6…

【MySQL】 复合查询 | 内外连接

文章目录 1. 复合查询多表笛卡尔积自连接在where子句使用子查询单行子查询多行子查询in关键字all关键字any关键字 多列子查询 在from子句中使用子查询合并查询unionunion all 2. 内连接3. 外连接左外连接右外连接 1. 复合查询 多表笛卡尔积 显示雇员名、雇员工资以及所在部门…

基于Electron27+React18+ArcoDesign客户端后台管理EXE

基于electron27.xreact18搭建电脑端exe后台管理系统模板 electron-react-admin 基于electron27整合vite.jsreact18搭建桌面端后台管理程序解决方案。 前几天有分享electron27react18创建跨平台应用实践&#xff0c;大家感兴趣可以去看看。 https://blog.csdn.net/yanxinyun1990…

Unit1_1:分治问题之时间复杂度求解

文章目录 背景递归树法案例一案例二局限性 代入法/替代法主方法&#xff08;重点&#xff09; 背景 当碰到形如 T ( n ) a T ( ⌈ n b ⌉ ) O ( n d ) T(n)aT(\lceil \frac{n}{b} \rceil)O(n^d) T(n)aT(⌈bn​⌉)O(nd)的递推式&#xff0c;本质上就是将问题转化为规模更小的…

【MySQL数据库】初识MySQL数据库、安装MySQL

文章目录 前言一、什么是 MySQL&#xff1f;二、MySQL 的强大之处三、Ubuntu安装MySQL步骤 1: 更新包列表步骤 2: 安装 MySQL步骤 3: 启动 MySQL 服务步骤 4: 验证 MySQL 安装步骤 5: 确保 MySQL 安全性 总结 前言 在今天的数字化世界中&#xff0c;数据是企业和个人的重要资产…

BUUCTF qr 1

BUUCTF:https://buuoj.cn/challenges 题目描述&#xff1a; 这是一个二维码&#xff0c;谁用谁知道&#xff01; 密文&#xff1a; 下载附件&#xff0c;得到一张二维码图片。 解题思路&#xff1a; 1、这是一道签到题&#xff0c;扫描二维码得到flag。 flag&#xff1a;…

Java进阶(List)——面试时List常见问题解读 结合源码分析

前言 List、Set、HashMap作为Java中常用的集合&#xff0c;需要深入认识其原理和特性。 本篇博客介绍常见的关于Java中List集合的面试问题&#xff0c;结合源码分析题目背后的知识点。 其他相关的List的文章合集如下&#xff1a; 手动实现ArrayList & 源码的初步理解分析…