HashMap和Hashtable的比较是Java面试中的常见问题,用来考验程序员是否能够正确使用集合类以及是否可以随机应变使用多种思路解决问题。HashMap的工作原理、ArrayList与Vector的比较以及这个问题是有关Java 集合框架的最经典的问题。Hashtable 在Java 4中被重写了,实现了Map接口,所以自此以后也成了Java集合框架中的一部分。Hashtable和HashMap在Java面试中相当容易被问到,甚至成为了集合框架面试题中最常被考的问题,所以在参加任何Java面试之前,都不要忘了准备这一题。
这篇文章中,我们不仅将会看到HashMap和Hashtable的区别,还将看到它们之间的相似之处。
HashMap和Hashtable的区别:
1.类的定义:
HashMap:
public class HashMap<K,V> extends AbstractMap<K,V>
implements Map<K,V>, Cloneable, Serializable
Hashtable:
public class Hashtable<K,V>
extends Dictionary<K,V>
implements Map<K,V>, Cloneable, java.io.Serializable
a、第一点不同:
Hashtable 继承了 Dictionary 类,而HashMap实现了 AbstractMap 类。
2. put方法
HashMap:
public V put(K key, V value) {
//允许 value 的值为空
return putVal(hash(key), key, value, false, true);
}
static final int hash(Object key) {
int h;
return (key == null) ? 0 : (h = key.hashCode()) ^ (h >>> 16); //允许 key 的值为空值
}
Hashtable:
public synchronized V put(K key, V value) {//线程同步
// Make sure the value is not null
if (value == null) {
//不允许 value 的值为空,否则抛出空指针异常
throw new NullPointerException();
}
// Makes sure the key is not already in the hashtable.
Entry<?,?> tab[] = table;
// 若 key 的值为空会在这一步抛出空指针异常
int hash = key.hashCode();
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)) {
V old = entry.value;
entry.value = value;
return old;
}
}
addEntry(hash, key, value, index);
return null;
}
b、第二点不同:
- HashMap 不是同步的,存在线程安全问题;Hashtable 是同步的,线程是安全的。
- 因为 Hashtable 是线程同步的,所以在效率上 HashMap 的储存效率会比 HashMap 的效率低。
HashMap允许 key 和 value 的值都为空,而 Hashtable 不允许 key 和 value 的值为空,否则会抛出空指针异常。
3.方法上的不同
HashMap:
Hashtable:
HashTable 的 containsValue 方法
public boolean containsValue(Object value) {
return contains(value);
}
c、第三点不同:
HashMap 包含containsKey 和 containsValue 方法,而Hashtable 包含 contains、containsKey 和 containsValue 方法(contains 在功能上等同于 containsValue 方法,containValue 是 collection 框架中 Map 接口的一部分)。
总结:
1.
HashMap 是 Hashtable 的轻量级实现(非线程安全的实现),他们都完成了 Map 接口,主要区别在于 HashMap 允许空(null)键值(key),由于非线程安全,效率上可能高于 Hashtable。 HashMap 允许将 null 作为 key 或者value,而 Hashtable 不允许。 HashMap 把Hashtable 的 contains 方法去掉了。因为contains方法容易让人引起误解。 Hashtable 继承自 Dictionary 类,而 HashMap 继承自 Dictionary。 最大的不同是,Hashtable 的方法是 Synchronize 的,而 HashMap 不是,在多个线程访问 Hashtable 时,不需要自己为它的方法实现同步,而 HashMap 就必须为之提供外同步。 Hashtable 和 HashMap 采用的 hash/rehash 算法都大概一样,所以性能不会有很大的差别。
2.
将 HashMap 同步:
HashMap可以通过下面的语句进行同步:
Map m = Collections.synchronizeMap(hashMap);
3.常见的线程安全的集合
vector:就比arraylist多了个同步化机制(线程安全),因为效率较低,现在已经不太建议使用。在web应用中,特别是前台页面,往往效率(页面响应速度)是优先考虑的;
statck:堆栈类,先进后出;
hashtable:就比 hashmap 多了个线程安全;
enumeration:枚举,相当于迭代器;
4.常见的线程安全的类
StringBuffer是线程安全,而StringBuilder是线程不安全的,因此 StringBuilder 的效率比 StringBuffer 高。
帅照: