Java集合之Map接口與實現(xiàn)類詳解
初識Map
Map接口沒有從Collection接口繼承,Map接口用于維護(hù)“鍵-值”對數(shù)據(jù),這個“鍵-值”對就是Map中的元素,Map提供“鍵(Key)”到“值(value)”的映射,一個Map中鍵值必須是唯一的,不能有重復(fù)的鍵,因為Map中的“鍵-值”對元素是通過鍵來唯一標(biāo)識的,Map的鍵是用Set集合來存儲的,所以充當(dāng)鍵元素的類必須重寫hashCode()和equals()方法,通過鍵元素來檢索對應(yīng)值元素
Map中常用方法
V put(K key, V value) //向Map集合中添加鍵值對 V get(Object key) //返回指定鍵映射到的值,通過key獲取value void clear() //從此映射中刪除所有映射,清空Map集合 boolean containsKey(Object key) //判斷Map是否包含某個key boolean containsValue(Object value) //判斷Map是否包含某個value boolean isEmpty() //判斷Map中元素個數(shù)是否為0 Set<K> keySet() //獲取Map集合中所有的key(所有的鍵都是一個“Set集合”) V remove(Object key) //通過key刪除鍵值對,如果存在,則從該映射中移除鍵的映射(可選操作) int size() //獲取Map集合中鍵值對的個數(shù)
HashMap
HashMap特點
(1)HashMap實現(xiàn)了Map 接口
(4)HashMap以Hash表為基礎(chǔ)構(gòu)建
(2)HashMap 允許鍵(Key)為空和值(Value)為空
(3)HashMap不是線程安全的,不能用在多線程環(huán)境中
HashMap常用的構(gòu)造方法如下
(1)HashMap():創(chuàng)建一個空 HashMap 對象,并為其分配默認(rèn)的初始容量和加載因子
(2)HashMap(int initialCapacity):創(chuàng)建一個空 HashMap 對象,并為其分配指定的初始容量
(3)HashMap(int initialCapacity,float loadFactor);創(chuàng)建一個空 HashMap 對象,并其分配指定的初始容量和加載因子
(4)HashMap(Map m):創(chuàng)建一個與給定Map 對象具有相同鍵-值對的 HashMap 對象
HashMap方法的簡單使用
import java.security.Key;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Set;
public class Warehouse1 {
public static void main(String[] args){
HashMap<String,Integer> hashMap=new HashMap<>();
hashMap.put("年齡",20);
hashMap.put("身高",180);
hashMap.put("體重",60);
System.out.println("鍵為年齡所對應(yīng)的值為:"+hashMap.get("年齡"));
System.out.println("該map是否包含鍵為“年齡”?"+hashMap.containsKey("年齡"));
System.out.println("該map是否包含鍵值為90?"+hashMap.containsValue(90));
System.out.println("該map是否為空?"+hashMap.isEmpty());
System.out.println("該map的長度大小為:"+hashMap.size());
System.out.println("移除鍵為“體重“的鍵值對"+hashMap.remove("體重"));
System.out.println("哈希映射中的內(nèi)容如下:"+hashMap);
Set<String> keys=hashMap.keySet();
Iterator<String> iterator=keys.iterator();
System.out.println("hashmap中的元素如下:");
while(iterator.hasNext()){
String s= iterator.next();
Integer name= hashMap.get(s);
System.out.println(s+":"+name);
}
}
}
輸出:
鍵為年齡所對應(yīng)的值為:20
該map是否包含鍵為“年齡”?true
該map是否包含鍵值為90?false
該map是否為空?false
該map的長度大小為:3
移除鍵為“體重“的鍵值對60
哈希映射中的內(nèi)容如下:{年齡=20, 身高=180}
hashmap中的元素如下:
年齡:20
身高:180
小tips:在輸出map中的元素時,我們不能直接使用iterator[迭代器],對元素進(jìn)行遍歷輸出,因為迭代只能用在Set/List這種單列存放數(shù)據(jù)的集合中,而map是雙列的,并且也不能使用foreach語句對map進(jìn)行輸出,因為foreach語句的本質(zhì)也是迭代,只能用在單列集合中。
LinkedHashMap
LinkedHashMap有如下特點
1:LinkedHashMap實現(xiàn)了Map接口
2:LinkedHashMap繼承了HashMap,內(nèi)部還有一個雙向鏈表維護(hù)鍵-值對的順序,每個鍵-值對即位于哈希表中,也位于雙向鏈表中
3:LinkedHashMap保存了兩種元素順序,輸入順序和訪問順序,插入順序是指先添加的元素在前面,后添加的元素在后面,修改對應(yīng)的元素不會影響元素的順序,訪問順序指的是get/put操作,對一個鍵執(zhí)行put/get操作后,其對應(yīng)的鍵-值對會移動到鏈表末尾,所以最末尾的元素是最近訪問的,最開始的是最久沒有被訪問的
4:LinkedHashMap不是線程安全的,不能用在多線程環(huán)境中
LinkedHashMap的構(gòu)造方法如下
1:LinkedHashMap();構(gòu)造一個空的LinkedHashMap對象
2:LinkedHashMap(Map m);構(gòu)造一個具有和給定Map相同鍵-值對的LinkedHashMap對象
3:LinkedHashMap(int capacity):構(gòu)造一個給定初始容量capacity的LinkedHashMap對象
4:LinkedHashMap(int capacity,float fillRatio):構(gòu)造一個給定初始容量capacity和填充比fillRatio的LinkedHashMap對象
5:LinkedHashMap(int capacity,float fillRatio,boolean accessOrder):構(gòu)造一個給定初始容量capacity,填充比fillRatio以及是否被訪問順序的LinkedHashMap對象,access-sOrder為true表示按訪問順序,否則按插入順序。
注:前四種構(gòu)造方法創(chuàng)建的LinkedHashMap對象都是按插入順序
注:fillRatio是裝載因子,范圍在0-1.0之間,默認(rèn)是0.75。當(dāng)實際元素個數(shù)/容量 > fillRatio, HashMap自動進(jìn)行擴(kuò)容,以保證檢索速度
舉例:
分別創(chuàng)建兩個LinkedHashMap對象-----linkedHashMap和linkedHashMap1
linkedHashMap是以上述五種方法中的第一種構(gòu)造的LinkedHashMap對象,而linkedHashMap1是以上述五種方法中的第5種構(gòu)造的LinkedHashMap對象.
代碼如下:
import java.security.Key;
import java.util.*;
public class Warehouse1 {
public static void main(String[] args){
LinkedHashMap<String,Integer> linkedHashMap=new LinkedHashMap<>();
linkedHashMap.put("number1",10);
linkedHashMap.put("number2",20);
linkedHashMap.put("number3",30);
linkedHashMap.put("number4",40);
linkedHashMap.get("number1");
linkedHashMap.get("number4");
Set <Map.Entry<String,Integer>> sets=linkedHashMap.entrySet();//Map.Entry是Map的一個內(nèi)部類,表達(dá)一個 key/value映射關(guān)系
System.out.println("linkedHashMap中的元素為:");
for(Map.Entry<String,Integer> entry:sets) {
System.out.println("鍵為:" + entry.getKey() + ",值為:" + entry.getValue());
}
System.out.println("---------------");
LinkedHashMap<String,Integer> linkedHashMap1=new LinkedHashMap<String,Integer>(3,0.5f,true);
linkedHashMap1.put("number1",10);
linkedHashMap1.put("number2",20);
linkedHashMap1.put("number3",30);
linkedHashMap1.put("number4",40);
linkedHashMap1.get("number1");
linkedHashMap1.get("number4");
linkedHashMap1.put("number3",1000);
Set<Map.Entry<String,Integer>> set=linkedHashMap1.entrySet();
System.out.println("linkedHashMap1中的元素為:");
for(Map.Entry<String ,Integer> entry1:set) {
System.out.println("鍵為:" + entry1.getKey() + "值為:" + entry1.getValue());
}
}
}
輸出:
linkedHashMap中的元素為:
鍵為:number1,值為:10
鍵為:number2,值為:20
鍵為:number3,值為:30
鍵為:number4,值為:40
---------------
linkedHashMap1中的元素為:
鍵為:number2值為:20
鍵為:number1值為:10
鍵為:number4值為:40
鍵為:number3值為:1000
通過輸出結(jié)果,我們不難發(fā)現(xiàn),linkedHashMap中的元素輸出的順序為我們插入時的順序,而linkedHashMap1中的元素輸出順序為訪問順序,由于這種構(gòu)造對象的方法,我們設(shè)置了access-sOrder為true,因此輸出順序按訪問順序,linkedHashMap1.get(“number1”),表示訪問number1,訪問完之后,該鍵值對就移動到最后,下面兩行的操作產(chǎn)生的影響也是這樣linkedHashMap1.get(“number4”);linkedHashMap1.put(“number3”,1000)。
當(dāng)按照訪問順序時,put和get去操作已經(jīng)存在的Entry時,都會把Entry移動到雙向鏈表的表尾[實際是先刪除再插入]
TreeMap
TreeMap有如下特點
1:TreeMap實現(xiàn)了SortedMap接口
2:TreeMap和實現(xiàn)Map的其他對象不同的是,它不具有調(diào)優(yōu)選項
3:TreeMap中所有元素必須是可比較的
4:TreeMap不是線程安全的
TreeMap的構(gòu)造方法如下
1:TreeMap():構(gòu)造一個空的TreeMap對象
2:TreeMap(Map m):構(gòu)造一個具有和給定Map相同鍵-值對的TreeMap對象
3:TreeMap(Comparator c):構(gòu)造一個空的TreeMap對象,并且規(guī)定特定的排列方式
4:TreeMap(SortedMap a):構(gòu)造一個與給定的SortedMap具有相同鍵-值對,相同排列規(guī)則的TreeMap對象
TreeMap方法的簡單使用
import java.util.*;
public class Warehouse1 {
public static void main(String[] args) {
TreeMap<String,String> treeMap=new TreeMap<>();
treeMap.put("水果","蘋果");
treeMap.put("汽車","奔馳");
treeMap.put("城市","西安");
System.out.println("映射中的元素是:"+treeMap);
Set<String> keySet=treeMap.keySet();
Iterator<String> iterator=keySet.iterator();
System.out.println("TreeMap類實現(xiàn)的Map映射,按鍵值升序排列元素如下:");
while(iterator.hasNext()){
String it=iterator.next();
String name=treeMap.get(it);
System.out.println(it+":"+name);
}
}
}輸出:
映射中的元素是:{城市=西安, 水果=蘋果, 汽車=奔馳}
TreeMap類實現(xiàn)的Map映射,按鍵值升序排列元素如下:
城市:西安
水果:蘋果
汽車:奔馳
注:TreeMap默認(rèn)排序規(guī)則:按照key的字典順序來排序[升序],當(dāng)然也可以通過Comparator接口,去自定義排序規(guī)則。
HashMap和TreeMap的比較
HashMap和TreeMap在實際應(yīng)用中要使用哪一個,還是需要根據(jù)實際情況進(jìn)行分析,在Map中插入,刪除和定位元素,HashMap是最好的選擇,但是如果要按順序遍歷鍵,那么TreeMap會更好,根據(jù)集合大小,先把元素添加到HashMap,再把這種映射轉(zhuǎn)換成一個用于有序鍵遍歷的TreeMap會更快,使用HashMap要求添加的鍵類明確定義了hashcode()實現(xiàn),有了TreeMap實現(xiàn),添加到映射的元素一定是可排序的。
Hashtable
Hashtable有如下特點
1:Hashtable實現(xiàn)了map接口
2:Hashtable以Hash表基礎(chǔ)構(gòu)建
3:Hashtable和HashMap在執(zhí)行過程中具有一定的相似性
4:Hashtable中不允許空元素,即鍵和值都不允許為空
5:Hashtable是線程安全的,可以在多線程環(huán)境中使用
Hashtable的四個構(gòu)造方法如下
Hashtable();創(chuàng)建一個空Hashtable對象,并為其分配默認(rèn)的初始容量和加載因子
Hashtable(int initialcapacity);創(chuàng)建一個空Hashtable對象,并為其分配指定的初始容量
Hashtable(int initialcapacity,float loadFactor):創(chuàng)建一個空Hashtable對象,并指定其初始容量和加載因子
Hashtable(Map m);創(chuàng)建一個與給定Map對象具有相同鍵-值對的Hashtable對象
Hashtable新增的常用方法
舉例:
import java.util.*;
public class Warehouse1 {
public static void main(String[] args) {
Hashtable<String,Double> hashtable=new Hashtable<>();
hashtable.put("王俊凱",new Double(350.55));
hashtable.put("王源",new Double(3250.55));
hashtable.put("易烊千璽",new Double(1350.55));
Enumeration<String> names=hashtable.keys();
while(names.hasMoreElements()){
String name=names.nextElement();
System.out.println(name+":"+hashtable.get(name));
}
double new_double=hashtable.get("易烊千璽").doubleValue();
hashtable.put("易烊千璽",new Double(new_double+2000));
System.out.println("易烊千璽的新余額為:"+hashtable.get("易烊千璽"));
}
}輸出:
易烊千璽:1350.55
王源:3250.55
王俊凱:350.55
易烊千璽的新余額為:3350.55
集合中元素的遍歷
Collection接口的iterator()方法返回一個iterator對象,iterator接口能以迭代方式逐個訪問集合中各個元素,并安全地從Collection中除去適當(dāng)?shù)脑?,iterator接口中定義的方法如下所示:
iterator接口中的方法
- boolean hasNext();判斷游標(biāo)右邊是否還有元素
- Object next();返回游標(biāo)右邊的元素并將游標(biāo)移動到該元素后
- void remove();刪除游標(biāo)左邊的元素,通常在next()方法之后執(zhí)行,只執(zhí)行一次
Enumeration接口的功能與iterator接口類似,也能夠?qū)现械脑剡M(jìn)行遍歷,但是Enumeration接口只對Vector,Hashtable類提供遍歷方法,并且不支持移除操作,實現(xiàn)Enumeration接口的對象,它生成一系列元素,一次生成一個,連續(xù)調(diào)用,nextElement方法將返回一系列的連續(xù)元素
Enumeration接口中的方法
boolean hasMoreELements(); 如果存在訪問的更多元素,則返回true
Object nextEment(); 返回下一個元素的引用
到此這篇關(guān)于Java集合之Map接口與實現(xiàn)類詳解的文章就介紹到這了,更多相關(guān)Java Map接口內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
SpringBoot與SpringCloud的版本對應(yīng)關(guān)系解讀
本文介紹了SpringBoot與SpringCloud的版本對應(yīng)關(guān)系,提供了一個官方的版本對應(yīng)表,并給出了個人的一些經(jīng)驗總結(jié)2024-12-12
解決maven中只有Lifecycle而Dependencies和Plugins消失的問題
這篇文章主要介紹了maven中只有Lifecycle而Dependencies和Plugins消失的問題及解決方法,本文通過圖文的形式給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友參考下吧2020-07-07
Spring?Cloud?Gateway?服務(wù)網(wǎng)關(guān)的部署與使用詳細(xì)講解
這篇文章主要介紹了Spring?Cloud?Gateway?服務(wù)網(wǎng)關(guān)的部署與使用詳細(xì)介紹,本文給大家講解的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下2023-04-04
spring學(xué)習(xí)之參數(shù)傳遞與檢驗詳解
這篇文章主要給大家介紹了關(guān)于spring參數(shù)傳遞與檢驗的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作能帶來一定的幫助,需要的朋友們下面跟著小編來一起學(xué)習(xí)學(xué)習(xí)吧。2017-07-07

