Java入門學習- 理解List和HashMap和HashTable的用法和區別

gongjinsi發表於2017-05-05

一、 List、HashMap和HashTable的關係與區別

  • List是介面,特性是按順序,可以重複
  • HashMap,實現了map介面,是鍵值對(key-value)
  • HashTable ,實現了map介面。繼承於dictionary,他與HashMap的區別可以從下面的引用總結為一下幾點:
    • HashTable是同步支援多執行緒的。HashMap不支援,但是Jdk1.5之後,ConcurrentHashMap支援了。
    • HashTable不允許null鍵和值,HashMap允許
    • HashMap是HashTable輕量級的實現

下圖可以很清楚的說明List和HashMap的關係
集合類

HashMap和HashTable我引用了下面一段話

HashMap和Hashtable都實現了Map介面,但決定用哪一個之前先要弄清楚它們之間的分別。主要的區別有:執行緒安全性,同步(synchronization),以及速度。

HashMap是非synchronized,而Hashtable是synchronized,這意味著Hashtable是執行緒安全的,多個執行緒可以共享一個Hashtable;而如果沒有正確的同步的話,多個執行緒是不能共享HashMap的。Java 5提供了ConcurrentHashMap,它是HashTable的替代,比HashTable的擴充套件性更好。

另一個區別是HashMap的迭代器(Iterator)是fail-fast迭代器,而Hashtable的enumerator迭代器不是fail-fast的。所以當有其它執行緒改變了HashMap的結構(增加或者移除元素),將會丟擲ConcurrentModificationException,但迭代器本身的remove()方法移除元素則不會丟擲ConcurrentModificationException異常。但這並不是一個一定發生的行為,要看JVM。這條同樣也是Enumeration和Iterator的區別。

由於Hashtable是執行緒安全的也是synchronized,所以在單執行緒環境下它比HashMap要慢。如果你不需要同步,只需要單一執行緒,那麼使用HashMap效能要好過Hashtable。

HashMap不能保證隨著時間的推移Map中的元素次序是不變的。

hashMap去掉了HashTable 的contains方法,但是加上了containsValue()和containsKey()方法

二、List、HashMap和HashTable的小例子

//ArrayList的栗子
public class CollectionTest {
    public static void main(String[] args) {
        Collection<String> c =new ArrayList<String>();  //ArrayList屬於Collection,所以可以用它的宣告
        c.add("張三");
        c.add("李四");
        c.add("王五");
        System.out.println(c);
        Collection<String > d=new ArrayList<String>();
        d.add("趙六");
        d.add("馮七");
        c.addAll(d);   //新增其他ArrayList
        System.out.println(c);
        c.addAll(c);   //新增自己
        System.out.println(c);//由此說明List只是有序,但是可以重複
        System.out.println("c是否完全包含著d:"+c.containsAll(d));    //是否包含另一個ArrayList
        System.out.println("c是否包含著趙六:"+c.contains("趙六"));
        //迭代器遍歷
        Iterator it=c.iterator();
        while(it.hasNext()){
            System.out.print(it.next()+"--");
        }
        /*
         * iterator遍歷效能次之,最好為
         * for(int i = 0; i < list.size(); i++) {  
            list.get(i);     //因為collection沒有get()方法,所以若需要用,就改為List<String> c =new ArrayList<String>();
            }  
         */
        System.out.println();
        c.removeAll(d);  //刪除陣列列表d
        System.out.println(c);
        c.remove("李四");//會刪除第一個遇到的李四
        System.out.println(c);
        Collection<String> f=new ArrayList<String>();
        f.add("王五");
        c.removeAll(f);//這樣就會刪除所有的王五,但是不能這樣寫c.removeAll("王五");
        System.out.println(c);
        c.clear();  //清空c
        System.out.println(c);
    }
}
// 輸出
/*
[張三, 李四, 王五]
[張三, 李四, 王五, 趙六, 馮七]
[張三, 李四, 王五, 趙六, 馮七, 張三, 李四, 王五, 趙六, 馮七]
c是否完全包含著d:true
c是否包含著趙六:true
張三--李四--王五--趙六--馮七--張三--李四--王五--趙六--馮七--
[張三, 李四, 王五, 張三, 李四, 王五]
[張三, 王五, 張三, 李四, 王五]
[張三, 張三, 李四]
[]
*/
//HashMap和HashTable的栗子
public class HashMapTest {

    public static void main(String[] args) {
        Map m=new HashMap<String,String>();
        m.put("sky","blue");
        m.put("tree",   "green");
        m.put("flower", "red");
        m.put("balana","yellow");
        System.out.println(m.values());  //輸出所有的值,返回的是一個集合,[blue, yellow, green, red]
        System.out.println(m.keySet());//輸出所有的鍵,返回一個set():[sky, balana, tree, flower]。因為set是不允許重複的,體現了鍵的唯一性
        System.out.println(m.hashCode());//返回m特有的hashcode:859049909
        System.out.println(m.equals(m));//判斷是是否相等:true
        System.out.println(m.entrySet());//輸出鍵值對:[sky=blue, balana=yellow, tree=green, flower=red]
        System.out.println(m.get("tree"));//通過鍵得到值:green
        System.out.println(m.remove("flower")); //刪除,會返回刪除鍵的值:red
        System.out.println(m);//刪除成功:{sky=blue, balana=yellow, tree=green}
        //下面為hashtable,確實兩個類的方法都差不多
        Hashtable t=new Hashtable<String,String>();
        t.put("sky","blue");
        t.put("tree",   "green");
        t.put("flower", "red");
        t.put("balana","yellow");
        System.out.println(t.values());  //[green, red, yellow, blue]
        System.out.println(t.keySet());//[tree, flower, balana, sky]
    }

}

三、學習過程中,看到兩篇文章特別好,做個記錄

1、HashMap底層實現原理/HashMap與HashTable區別/HashMap與HashSet區別 (面試題部分寫得很好)
http://www.cnblogs.com/beatIteWeNerverGiveUp/p/5709841.html
2、HashMap對HashCode碰撞的處理
http://blog.csdn.net/caisini_vc/article/details/52452498

介於現在知識廣度不夠和時間太少, 只是粗略看了一下,沒有仔細分析。之後有時間再加深深度

相關文章