转自https://blog.csdn.net/duoduo18up/article/details/80167074

1.定义

public class Hashtable<K,V> extends Dictionary<K,V>implements Map<K,V>,Cloneable,java.io.Serializable

继承自Dictionary。

  • Dictionary是一个抽象父类,功能和Map一样,但过时了,官方推荐使用Map接口来替代。

实现了Map接口,以及Cloneable,Serializable接口。

2.和HashMap的区别

2.1 null值的问题

Hashtable的键(key)和值(value)均不能为null

/**
* 将key和value加入到map中,明显标明,
* value不能为null。如果key为null,则会报NullPointerException异常
* */
public synchronized V put(K key, V value) {// Make sure the value is not nullif (value == null) {throw new NullPointerException();}// Makes sure the key is not already in the Hashtable.Entry<?,?> tab[] = table;int hash = key.hashCode();//很直接的利用hashCode去除table.length,然后取长度。int index = (hash & 0x7FFFFFFF) % tab.length;@SuppressWarnings("unchecked")Entry<K,V> entry = (Entry<K,V>)tab[index];//链表后面有数据for(; entry != null ; entry = entry.next) {if ((entry.hash == hash) && entry.key.equals(key)) {//hash相同且equals,那么就连在后面,是用链表的方式。V old = entry.value;entry.value = value;return old;}}//第一个,链表后面没有数据。addEntry(hash, key, value, index);return null;
}

关于value,明显有if判断,不能为null。

如果key为null,则也直接在计算hashCode的时候就会报空指针异常。

2.2 计算table数组索引值的方法

int hash=key.hashCode();//直接用hashcode%n
int index=(hash&0x7FFFFFFF)%tab.length

而HashMap中:

int index=e.hash%n;

hash值的计算方法不同,很直接地利用hashCode去除table.length,然后取余数。

2.3 Hashtable是线程安全的

因为Hashtable中的大多数方法都是加了synchronized关键字,所以同一时刻只能有一个线程进入其方法,故是线程安全的。

2.4initialCapacity和loadFactor

HashMap中:initialCapacity=16,loadFactor=0.75;

Hashtable中:initialCapacity=11,loadFactor=0.75;

2.5解决冲突的方式

HashMap:链表/红黑树

  • 冲突数量<8,以链表方式解决冲突
  • 冲突数量>=8,将冲突的Entry转换为红黑树进行存储
  • 又当冲突数量<6时,有转换为链表进行存储

Hashtable:只有链表

2.6 扩容的额度

HashMap中:一旦扩容,都是扩展到2的倍数。因为这样有利于计算数组索引值。即,和计算数组索引结合起来

Hashtable中:一次性扩展为oldCapacity*2+1

/*** 一次扩展是,old*2+1
*/
@SuppressWarnings("unchecked")
protected void rehash() {int oldCapacity = table.length;Entry<?,?>[] oldMap = table;// overflow-conscious codeint newCapacity = (oldCapacity << 1) + 1;if (newCapacity - MAX_ARRAY_SIZE > 0) {if (oldCapacity == MAX_ARRAY_SIZE)// Keep running with MAX_ARRAY_SIZE bucketsreturn;newCapacity = MAX_ARRAY_SIZE;}Entry<?,?>[] newMap = new Entry<?,?>[newCapacity];modCount++;//新的threshold值。取newCapacity*loadFactor的小值。threshold = (int)Math.min(newCapacity * loadFactor, MAX_ARRAY_SIZE + 1);table = newMap;for (int i = oldCapacity ; i-- > 0 ;) {for (Entry<K,V> old = (Entry<K,V>)oldMap[i] ; old != null ; ) {Entry<K,V> e = old;old = old.next;int index = (e.hash & 0x7FFFFFFF) % newCapacity;e.next = (Entry<K,V>)newMap[index];newMap[index] = e;}}
}

先扩展,再把就数组里面的元素一个一个添加到新的里面。

注意:这里取hash而不是e.hash,而仍然是key.hashCode计算保留下来的值。

Hashtable源码分析相关推荐

  1. Java源码详解三:Hashtable源码分析--openjdk java 11源码

    文章目录 注释 哈希算法与映射 线程安全的实现方法 put 操作 get操作 本系列是Java详解,专栏地址:Java源码分析 Hashtable官方文档:Hashtable (Java Platfo ...

  2. Java集合:Hashtable源码分析

    1. 概述 上次讨论了HashMap的结构,原理和实现,本文来对Map家族的另外一个常用集合HashTable进行介绍.HashTable和HashMap两种集合非常相似,经常被各种面试官问到两者的区 ...

  3. 【Java源码分析】HashTable源码分析

    类的定义 public class Hashtable<K,V> extends Dictionary<K,V> implements Map<K,V>, Clon ...

  4. Java集合之Hashtable源码分析

    概述 Hashtable也是基于哈希表实现的, 与map相似, 不过Hashtable是线程安全的, Hashtable不允许 key或value为null. 成员变量 Hashtable的数据结构和 ...

  5. Java学习集合源码分析

    集合源码分析 1.集合存在的原因 可以用数组来表示集合,那为什么还需要集合? 1)数组的缺陷 ​ 在创建数组时,必须指定长度,一旦指定便不能改变 数组保存必须是同一个类型的数据 数组的增加和删除不方便 ...

  6. ConcurrentHashMap实现原理及源码分析

    ConcurrentHashMap是Java并发包中提供的一个线程安全且高效的HashMap实现(若对HashMap的实现原理还不甚了解,可参考我的另一篇文章HashMap实现原理及源码分析),Con ...

  7. Redis 数据结构-字典源码分析

    2019独角兽企业重金招聘Python工程师标准>>> 相关文章 Redis 初探-安装与使用 Redis 数据结构-字符串源码分析 本文将从以下几个方面介绍 前言 字典结构图 字典 ...

  8. Java源码详解六:ConcurrentHashMap源码分析--openjdk java 11源码

    文章目录 注释 类的继承与实现 数据的存储 构造函数 哈希 put get 扩容 本系列是Java详解,专栏地址:Java源码分析 ConcurrentHashMap 官方文档:ConcurrentH ...

  9. Java源码详解二:HashMap源码分析--openjdk java 11源码

    文章目录 HashMap.java介绍 1.HashMap的get和put操作平均时间复杂度和最坏时间复杂度 2.为什么链表长度超过8才转换为红黑树 3.红黑树中的节点如何排序 本系列是Java详解, ...

最新文章

  1. Linux入门-7 Linux管道、重定向以及文本处理
  2. IDEA插件-生成对象所有set方法--->GenerateAllSetter
  3. 抽象类(c++细节篇九)
  4. html文件已传入服务器,把html文件上传到云服务器
  5. 程序猿值得看的几个技术网站(记录)
  6. 蓝桥杯 ADV-221 算法提高 7-1用宏求球的体积
  7. 用Word2007写Blog
  8. 仿51 job 省市二级联动
  9. MATLAB代码:基于分布式优化的多产消者非合作博弈能量共享
  10. docker安装网易云音乐(yesplaymusic)
  11. 雨滴win7计算机路径,Rainmeter雨滴桌面Win7打不开怎么办?
  12. element ui表单必填_elementUI 表单校验切换必填和非必填
  13. 避免过多if - else的新姿势:策略模式、工厂 + 策略
  14. 如何安装华为路由器模拟环境ENSP
  15. OS和Linux笔记
  16. 高校BBS最HOT的100个笑话(不看保证后悔终身)
  17. 深入剖析 grep 命令
  18. Android学习 书籍
  19. ROS自定义msg类型及使用
  20. python抓取网站88titienmae88中的“图片区”的第一页的所有图片

热门文章

  1. CentOS 7 使用Google-Authenticator进行多因素认证
  2. 外媒称Windows 10是一辆“广告大巴车”
  3. [Leetcode] Permutations 全排列
  4. [转]自适应网页设计(Responsive Web Design)
  5. jvm在不同系统中的最大内存空间地址
  6. 【计网】计算机网络期末总复习-谢希仁(个人总结)理论概念
  7. 【杂项】CUDA下找不到CUDA Sample文件
  8. linux fedora 35 彻底卸载idea2021.2.2
  9. linux shell 判断文件是否存在
  10. gorm框架:user role用户角色一对一关联Model编写