HashMap内部存储实现及HashTable比较

本文详细解析了HashMap的内部存储实现,通过源码分析了put和get操作的过程,指出HashMap基于"数组+链表"的哈希表结构。接着对比了HashMap与HashTable,强调了线程安全、null键值支持以及效率等方面的不同。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

一、HashMap的内部存储实现

HashMap底层实现的数据结构是哈希表。哈希表的实现一般有两种,第一种是数组(闭散列),第二种是数组+链表(开散列)。而HashMap采用的是“数组+链表”的实现,
即数组存储链表的头结点。
1、HashMap存储数据时进行put( key, value )的操作,源代码如下:

[java]  view plain copy 在CODE上查看代码片 派生到我的代码片
  1. public V put(K key, V value) {    
  2.         if (key == null)    
  3.             return putForNullKey(value);    
  4.         int hash = hash(key.hashCode()); //首先进行key.hashCode()操作,获取key的哈希值  
  5.         int i = indexFor(hash, table.length); //相当于:int i = hash % Entry[].length,Entry.length是数组长度  
  6.         for (Entry<K,V> e = table[i]; e != null; e = e.next) {    
  7.             Object k;    
  8.             if (e.hash == hash && ((k = e.key) == key || key.equals(k))) {    
  9.                 V oldValue = e.value;    
  10.                 e.value = value;    
  11.                 e.recordAccess(this);    
  12.                 return oldValue;    
  13.             }    
  14.         }  
  15.         modCount++;  
  16.         addEntry(hash, key, value, i);  
  17.         return null;    
  18. }  

注意:在Entry类里面有一个next属性,指向下一个Entry。例如,第一个键值对A进来,通过计算得到其key的hash是1,则存储:Entry[1]=A。接着,第二个键值对B进来,其key的hash也等于1,那么HashMap会这样做:B.next = A, Entry[1] = B,以此类推。由此可知,数组中存储的是最后插入的元素。


2、取出数据进行get( key )操作,源代码如下:

[java]  view plain copy 在CODE上查看代码片 派生到我的代码片
  1. public V get(Object key) {    
  2.         if (key == null)    
  3.             return getForNullKey();    
  4.         int hash = hash(key.hashCode());    
  5.         for (Entry<K,V> e = table[indexFor(hash, table.length)];    
  6.              e != null;    
  7.              e = e.next) {    
  8.             Object k;    
  9.             if (e.hash == hash && ((k = e.key) == key || key.equals(k)))    
  10.                 return e.value;    
  11.         }    
  12.         return null;    
  13. }  

当key不为空时,先根据hash函数得到hash值,再根据indexFor()得到数组的索引值,接着遍历链表。如果有key值等于已存在的key值,则返回其value。

二、HashMap和HashTable的比较
HashTable和HashMap采用相同的存储机制,二者的实现基本一致,不同的是:
1. HashMap是非线程安全的,HashTable是线程安全的。
2. HashMap的键和值都可以为null,但是HashTable不行。
3. 由于线程安全的关系,HashMap的效率比HashTable要高。

4. HashMap没有使用HashTable的contains()函数,取而代之的是containsKey()和containsValue()。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值