@南柯梦博客中的系列文章对Jdk中常用容器类ArrayList、LinkedList、HashMap、HashSet等的实现原理以代码注释的方式给予了说明(详见http://www.cnblogs.com/dongying/p/4022795.html#3045118等文章),而我在这里用另一种方式对其实现要点作一说明。

一、ArrayList和LinkedList的实现

  ArrayList和LinkList的实现原理比较简单,在关于Java的面试中经常被要求立即写出这两种容器类的简单实现。正如其名称所显示的,利用Java对泛型的支持在内部分别使用数组和双向链表存储元素,当容量不足时进行扩容,因而这两种容器类的适用场景基本对应于数组和链表的适用场景。

二、HashMap的实现之hash值

  HashMap的实现使用了内部类Entry,实际上存储在HashMap中的键值对就是使用Entry类型的数组来存储的,而Entry同时还是个单向无头链表,其用next属性指向下一个元素。存储键值对时首先得到key的hash值,并计算其在Entry数组中的存储位置,如方法indexFor所示:

static int indexFor(int h, int length) {
return h & (length-1);
}

即将hash值和Entry数组做按位与运算得到其应存储的位置索引。接下来的处理就是其中的精华了。如果该位置处是空的,则把代表键值对的Entry对象放入;否则位置处存在Entry链表,遍历该链表,如果有Entry节点的key值和待插入的Entry对象相等,则用新的value值替换旧值并返回旧值;如果没有相等的key值则把新的Entry对象放到链表头处。

三、相同hash值时键值对的存储结构

  总结一下,实际上这是不同key的hash值相同时的冲突处理方法。根据hash值的原理,相同元素其hash值必定相同,不同元素其hash值不一定相同。反过来讲,hash值相同的元素其值不一定相同,但hash值不同的元素其值一定不同。因此不同元素根据hash值以及indexFor()方法取得的索引值很可能是相同的,故需要在索引位置处用链表存储所有元素以供进一步甄别。由此可以推断出,HashMap的get()方法只能保证近似的O(1)时间复杂度。HashMap中的loadFactor属性也正是因为这个原因才存在的。进一步查看源码发现,Jdk8中HashMap的实现已有所变化,相同hash值的键值对是用链表和红黑树来共同实现的,具体使用哪种结构由冲突的key值个数决定。这样查找的时间复杂度得到了进一步优化,但同时增加了存储的时间,因为要涉及链表和红黑树的转换以及红黑树的再平衡等。

三、HashMap应用之HashSet

  而对于HashSet可以看做HashMap的一种特殊的使用,即对HashMap中所有的key值都存储相同的外部不可见的对象。

Java中HashMap等的实现要点浅析的更多相关文章

  1. Java中HashMap遍历的两种方式

    Java中HashMap遍历的两种方式 转]Java中HashMap遍历的两种方式原文地址: http://www.javaweb.cc/language/java/032291.shtml 第一种: ...

  2. 【转】 java中HashMap详解

    原文网址:http://blog.csdn.net/caihaijiang/article/details/6280251 java中HashMap详解 HashMap 和 HashSet 是 Jav ...

  3. java中HashMap详解(转)

    java中HashMap详解 博客分类: JavaSE Java算法JDK编程生活       HashMap 和 HashSet 是 Java Collection Framework 的两个重要成 ...

  4. java集合(2)- java中HashMap详解

    java中HashMap详解 基于哈希表的 Map 接口的实现.此实现提供所有可选的映射操作,并允许使用 null 值和 null 键.(除了非同步和允许使用 null 之外,HashMap 类与 H ...

  5. Java中HashMap的实现原理

    最近面试中被问及Java中HashMap的原理,瞬间无言以对,因此痛定思痛觉得研究一番. 一.Java中的hashCode和equals 1.关于hashCode hashCode的存在主要是用于查找 ...

  6. JAVA中hashmap的分析

    从http://blog.csdn.net/luanlouis/article/details/41576373?utm_source=tuicool&utm_medium=referral学 ...

  7. JAVA中HashMap相关知识的总结(一)

    Java中HashMap在jdk1.7和jdk1.8中的区别点: 在jdk1.7中是用数组+链表形式存储,1.8采用数组+链表/红黑树形式 Jdk1.8中由链表转为红黑树是长度大于8,由红黑树转为链表 ...

  8. java中HashMap的设计精妙在哪?

    摘要:本文结合图解和问题,教你一次性搞定HashMap 本文分享自华为云社区<java中HashMap的设计精妙在哪?用图解和几个问题教你一次性搞定HashMap>,作者:breakDaw ...

  9. java中HashMap的用法

    重点介绍HashMap.首先介绍一下什么是Map.在数组中我们是通过数组下标来对其内容索引的,而在Map中我们通过对象来对对象进行索引,用来索引的对象叫做key,其对应的对象叫做value.在下文中会 ...

随机推荐

  1. virtualbox 下windows与虚拟机实现文件共享---挂载

    1.创建挂载目录: mkdir /mnt/share 2.挂载:mount /dev/cdrom /mnt/share 3.cd /mnt/share 3.虚拟机-设备-分配光驱-VBoxGuestA ...

  2. WCF、WebAPI、WCFREST、WebService之间的区别

    注明:转载 在.net平台下,有大量的技术让你创建一个HTTP服务,像Web Service,WCF,现在又出了Web API.在.net平台下,你有很多的选择来构建一个HTTP Services.我 ...

  3. 原生js arguments 用法

    http://note.youdao.com/noteshare?id=fcd201e872e1ede16ce0057a1909f613

  4. Redis GetTypedClient

    C#操作Redis   未包含GetTypedClient定义 原创,转载请注明出处. VS版本:2015 用NuGet安装了Redis的包 按照百度的各种教程来操作,但是发现网上下载的DEMO可以正 ...

  5. Fatal error in launcher: Unable to create process using '"'

    今天遇到了 Fatal error in launcher: Unable to create process using '"' 这个问题,原来是我上次装python3.5的时候,pyth ...

  6. oracle10g、oracle client和plsql devement 三者之间的关系

    oracle10g是服务器,如果本机安装了oracle10g,没有必要安装oracle client,只要配置好DNS,就可以使用plsql devement连接     当然你也可以同时安装orac ...

  7. [Note] changing building platform from vs 2013 to vs community 2015

    The error turned out as "undefined linkage"(The same as you haven't use some function that ...

  8. Android studio下载依赖包很慢

    build gradle文件 buildscript { repositories { //jcenter() maven { url 'http://maven.oschina.net/conten ...

  9. fool

    from PIL import Imageimg = Image.open("D:\\pic2\\CZA3302.png")(w,h) = img.sizeim=img.conve ...

  10. Windows XP发行12周年,我正步入中年,你已垂暮

    2001年10月25日,Windows XP正式全球上市!作为Windows 2000的升级版本,XP拥有大量新的功能:新的用户界面.防火墙整合等,这些都大大的增强了系统的易用性和安全性.而微软将于2 ...