HashMap实现保存两个key相同的数据


Posted in Java/Android onJune 30, 2021

HashMap如何保存两个key相同的数据

最近一个朋友去面试了,面试官问了一个关于HashMap的问题:HashMap如何保存两个key相同的数据?

准确来说,应该是Map中如何保存两个key相同的数据,因为用来实现这个功能的IdentityHashMap类和HashMap虽然都是实现了Map接口,但本质是属于不同的东西;

我们知道在HashMap中,如果key相同就会被覆盖,那IdentityHashMap是怎么实现这个功能的呢?

java jdk源码中,IdentityHashMap类上写了100来行注释的代码,如果用一句话来总结的话:

IdentityhashMap类利用哈希表实现Map接口,比较键(和值)时使用引用相等性代替对象相等性,也就是说key(value)比较的时候只比较两个key是否引用同一个对象,比较的是对象的地址;

测试1:

public static void main(String[] args) {
    String str1 = "key";
    String str2 = "key";
    System.out.println(str1==str2);
    Map<String, String> map = new IdentityHashMap<>();
    map.put(str1, "value1");
    map.put(str2, "value2");
    map.forEach((k,v)-> System.out.println(k+"->"+v));
}

打印:

true

key->value2

测试1中,将字符串"key"直接赋值给str1和str2,因为字符串是放在常量池中的,所以str1和str2实际上还是同一个对象,所以它们的key值是相同的,会被覆盖;

测试2:

public static void main(String[] args) {
    String str1 = new String("key");
    String str2 = new String("key");
    System.out.println(str1==str2);
    Map<String, String> map = new IdentityHashMap<>();
    map.put(str1, "value1");
    map.put(str2, "value2");
    map.forEach((k,v)-> System.out.println(k+"->"+v));
}

打印:

false

key value1

key value2

测试2中,str1和str2是通过new的方式创建出来的,属于不同对象,所以它们的引用不同,key值也就不同,所以put的时候不会被覆盖;

关于IdentityHashMap常不常用,实际开发中我基本没用过,所以在什么场景会用到IdentityHashMap我也说不出个一二来;不过存在即合理,肯定有什么场景会用到的,后面遇到我会及时更新~

HashMap插入相同key

使用HashMap在插入操作时,会通过equal方法判断key是否相同。如果相同,则将覆盖对应的value;不相同才使用新的“桶”。

我的问题

当往HashMap中插入数据,即使有相同的key,但是能不能不进行覆盖操作,而是把新的value放在原有的value附近能够找到的位置?

想法

呃,其实大概方向就是通过一个HashMap<Integer, ArrayList>实现。。。

贴上代码

import java.util.ArrayList;
import java.util.HashMap; 
public class MapAndLink { 
    public static void main(String[] args){ 
        HashMap<Integer, ArrayList> map = new HashMap<>();
        put(1, 1, map);
        put(1, 3, map);
        put(2, 2, map);
        put(3, 4, map);
        put(1, 3, map);
        System.out.println(map.toString());
    }
 
    public static void put(Integer key, Integer str, HashMap<Integer, ArrayList> map){
        ArrayList<Integer> list = map.get(key);
        if(list == null)
            list = new ArrayList();
        for(int i = 0; i < list.size(); ++i){
            if(list.get(i).equals(str))
                return;
        }
        list.add(str);
        map.put(key, list);
    }
}

再贴上输出结果

{1=[1, 3], 2=[2], 3=[4]}

以上为个人经验,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Java/Android 相关文章推荐
Java中PriorityQueue实现最小堆和最大堆的用法
Jun 27 Java/Android
springboot拦截器无法注入redisTemplate的解决方法
Jun 27 Java/Android
解决ObjectMapper.convertValue() 遇到的一些问题
Jun 30 Java/Android
Java基础之this关键字的使用
Jun 30 Java/Android
springboot集成springCloud中gateway时启动报错的解决
Jul 16 Java/Android
Sleuth+logback 设置traceid 及自定义信息方式
Jul 26 Java/Android
使用jpa之动态插入与修改(重写save)
Nov 23 Java/Android
java objectUtils 使用可能会出现的问题
Feb 28 Java/Android
Dubbo+zookeeper搭配分布式服务的过程详解
Apr 03 Java/Android
Java异常体系非正常停止和分类
Jun 14 Java/Android
Java中的Kotlin 内部类原理
Jun 16 Java/Android
springboot集成redis存对象乱码的问题及解决
Jun 16 Java/Android
spring boot项目application.properties文件存放及使用介绍
springboot项目以jar包运行的操作方法
Springboot使用Spring Data JPA实现数据库操作
Jun 30 #Java/Android
如何给HttpServletRequest增加消息头
解决ObjectMapper.convertValue() 遇到的一些问题
Jun 30 #Java/Android
Java基础之详解HashSet的使用方法
Java实现多文件上传功能
Jun 30 #Java/Android
You might like
php 读取文件头判断文件类型的实现代码
2013/08/05 PHP
php实现递归与无限分类的方法
2015/02/16 PHP
初识laravel5
2015/03/02 PHP
PHP创建PowerPoint2007文档的方法
2015/12/10 PHP
PHP处理Ajax请求与Ajax跨域问题
2017/02/13 PHP
php检测mysql表是否存在的方法小结
2017/07/20 PHP
php无限级评论嵌套实现代码
2018/04/18 PHP
在 Laravel 6 中缓存数据库查询结果的方法
2019/12/11 PHP
Thinkphp 框架扩展之标签库驱动原理与用法分析
2020/04/23 PHP
jQuery 源代码显示控件 (Ajax加载方式).
2009/05/18 Javascript
学习ExtJS fit布局使用说明
2009/10/08 Javascript
基于jquery中children()与find()的区别介绍
2013/04/26 Javascript
一个非常全面的javascript URL解析函数和分段URL解析方法
2014/04/12 Javascript
JavaScript中this关键词的使用技巧、工作原理以及注意事项
2014/05/20 Javascript
javascript中使用new与不使用实例化对象的区别
2015/06/22 Javascript
jquery插件pagination实现无刷新ajax分页
2015/09/30 Javascript
安装使用Mongoose配合Node.js操作MongoDB的基础教程
2016/03/01 Javascript
jQuery post数据至ashx实例详解
2016/11/18 Javascript
认识jQuery的Promise的具体使用方法
2017/10/10 jQuery
解决vue中使用swiper插件问题及swiper在vue中的用法
2018/04/04 Javascript
Python删除指定目录下过期文件的2个脚本分享
2014/04/10 Python
Python cookbook(数据结构与算法)同时对数据做转换和换算处理操作示例
2018/03/23 Python
windows下 兼容Python2和Python3的解决方法
2018/12/05 Python
在OpenCV里使用Camshift算法的实现
2019/11/22 Python
python 安装库几种方法之cmd,anaconda,pycharm详解
2020/04/08 Python
pygame用blit()实现动画效果的示例代码
2020/05/28 Python
CSS3打造磨砂玻璃背景效果
2016/09/28 HTML / CSS
创意爱尔兰礼物:Creative Irish Gifts
2020/01/29 全球购物
工程师岗位职责
2013/11/08 职场文书
政府门卫岗位职责
2014/04/29 职场文书
批评与自我批评范文
2014/10/15 职场文书
考试作弊万能检讨书
2014/10/19 职场文书
致运动员的广播稿
2015/08/19 职场文书
SQL Server——索引+基于单表的数据插入与简单查询【1】
2021/04/05 SQL Server
世界无敌的ICOM IC-R9500宽频接收机
2022/03/25 无线电
SQL语句中EXISTS的详细用法大全
2022/06/25 MySQL