HashMap 和 Hashtable 的区别

2017-02-06  本文已影响65人  FTOLsXD

1.HashMap 是 Hashtable 的轻量级实现(非线程安全的实现),他们都完成了 Map 接口,主 要区别在于 HashMap 允许空(null)键值(key),由于非线程安全,在只有一个线程访问 的情况下,效率要高于 Hashtable。
2.HashMap 允许将 null 作为一个 entry 的 key 或者 value,而 Hashtable 不允许。 HashMap 把 Hashtable 的 contains 方法去掉了,改成 containsvalue 和 containsKey。因为
contains 方法容易让人引起误解。
3.Hashtable 继承自 Dictionary 类,而 HashMap 是 Java1.2引进的 Map interface 的一个实现。
4.最大的不同是,Hashtable 的方法是 Synchronize 的,而 HashMap 不是,在多个线程访问 Hashtable 时,不需要自己为它的方法实现同步,而 HashMap 就必须为之 供外同步。
Hashtable 和 HashMap 采用的 hash/rehash 算法都大概一样,所以性能不会有很大的差异。

备注hashMap和hashTable的遍历有两种方式:keySet和entrySet这里以hashMap为例

public class HashTableIteratorTest {
    public static void main(String[] args) {
        HashMap m = new HashMap();
        for(int i =0; i<1000;i++){
            m.put(""+i, "test");
        }
        keySetCostTimes(m);
        entrySetCostTimes(m);
    }
    public static void keySetCostTimes(HashMap m){
        long bs = Calendar.getInstance().getTimeInMillis();
        Iterator i = m.keySet().iterator();
        while(i.hasNext()){
            System.out.print(m.get(i.next()));
        }
        System.out.println();
        System.out.println(Calendar.getInstance().getTimeInMillis() - bs);
        
    }
    public static void entrySetCostTimes(HashMap m){
        long bs = Calendar.getInstance().getTimeInMillis();
        Iterator i = m.entrySet().iterator();
        while(i.hasNext()){
            Entry entry = (Entry) i.next();
            System.out.print(entry.getValue());
        }
        System.out.println();
        System.out.println(Calendar.getInstance().getTimeInMillis() - bs);
    }
}

运行结果

总结:
对于keySet其实是遍历了2次,一次是转为iterator,一次就从hashmap中取出key所对于的value。而entryset只是遍历了第一次,他把key和value都放到了entry中,所以就快了。

5.HashMap和hashTable的底层实现方式:

<li>他们的底层实现是通过初始化化一个Entry数组来实现key、value的保存。
<li>在他们的Entry中有四个变量,key、value、hash、next,其中next用于在hash方法添加值冲突时候,所指向的下一个值。
在HashMap和hashTable中添加值步骤
第一步,对key的hashcode进行hash计算,获取应该保存到数组中的index。(hashTable会首先判断key值是否为空,为空则抛出NullPointerException异常)
第二步,判断index所指向的数组元素是否为空,如果为空则直接插入。
第三步,如果不为空,则依次查找entry中next所指定的元素,判读key是否相等,如果相等,则替换久的值,返回。(hashTable会首先判断value值是否为空,为空则抛出NullPointerException异常)
第四步,如果都不相等,则将此链表头元素赋值给待插入entry的next变量,然后将待插入元素插入到entry数组中去。

上一篇下一篇

猜你喜欢

热点阅读