JDK 8中方便的新地图默认方法
Map接口在JDK 8中提供了一些方便的新方法 。 因?yàn)槲以诒疚闹薪榻B的Map方法是作為默認(rèn)方法實(shí)現(xiàn)的,所以Map接口的所有現(xiàn)有實(shí)現(xiàn)都享有默認(rèn)方法中定義的默認(rèn)行為,而無(wú)需任何新代碼。 這篇文章中介紹的JDK 8引入的Map方法是getOrDefault(Object,V) , putIfAbsent(K,V) ,remove(Object,Object), remove(Object,Object) , replace(K,V)和replace(K ,V,V) 。
演示示例圖
在本博文的所有示例中,我將使用以下代碼中所示的聲明和初始化Map 。 statesAndCapitals字段是類級(jí)別的靜態(tài)字段。 我特意只包含了美國(guó)五十個(gè)州中的一小部分,以使閱讀更加清晰,并使某些新的JDK 8 Map默認(rèn)方法的演示更加容易。
private final static Map statesAndCapitals;static{statesAndCapitals = new HashMap<>();statesAndCapitals.put("Alaska", "Anchorage");statesAndCapitals.put("California", "Sacramento");statesAndCapitals.put("Colorado", "Denver");statesAndCapitals.put("Florida", "Tallahassee");statesAndCapitals.put("Nevada", "Las Vegas");statesAndCapitals.put("New Mexico", "Sante Fe");statesAndCapitals.put("Utah", "Salt Lake City");statesAndCapitals.put("Wyoming", "Cheyenne");}Map.getOrDefault(Object,V)
Map的新方法getOrDefault(Object,V)允許調(diào)用者在單個(gè)語(yǔ)句中指定以獲取與提供的鍵對(duì)應(yīng)的映射值,或者如果找不到與提供的鍵匹配的返回值,則返回提供的“默認(rèn)值”鍵。
下一個(gè)代碼清單比較了如何在JDK 8之前實(shí)現(xiàn)與映射中提供的鍵相匹配的值的檢查,或者如果沒(méi)有找到匹配項(xiàng),則使用默認(rèn)值,以及如何在JDK 8中實(shí)現(xiàn)。
/** Demonstrate Map.getOrDefault and compare to pre-JDK 8 approach. The JDK 8* addition of Map.getOrDefault requires fewer lines of code than the* traditional approach and allows the returned value to be assigned to a* "final" variable.*/// pre-JDK 8 approach String capitalGeorgia = statesAndCapitals.get("Georgia"); if (capitalGeorgia == null) {capitalGeorgia = "Unknown"; }// JDK 8 approach final String capitalWisconsin = statesAndCapitals.getOrDefault("Wisconsin", "Unknown");Apache Commons類DefaultedMap提供的功能類似于新的Map.getOrDefault(Object, V)方法。 Groovy GDK包括一個(gè)與Groovy類似的方法Map.get(Object,Object) ,但是它的行為有些不同,因?yàn)槿绻也坏健?key”,它不僅會(huì)返回提供的默認(rèn)值,而且還會(huì)添加帶有基礎(chǔ)地圖的默認(rèn)值。
Map.putIfAbsent(K,V)
Map的新方法putIfAbsent(K,V)的 Javadoc公布了等效的默認(rèn)實(shí)現(xiàn):
The default implementation is equivalent to, for this map:V v = map.get(key);if (v == null)v = map.put(key, value);return v;另一個(gè)代碼示例對(duì)此進(jìn)行了說(shuō)明,該示例將JDK 8之前的方法與JDK 8的方法進(jìn)行了比較。
/** Demonstrate Map.putIfAbsent and compare to pre-JDK 8 approach. The JDK 8* addition of Map.putIfAbsent requires fewer lines of code than the* traditional approach and allows the returned value to be assigned to a* "final" variable.*/// pre-JDK 8 approach String capitalMississippi = statesAndCapitals.get("Mississippi"); if (capitalMississippi == null) {capitalMississippi = statesAndCapitals.put("Mississippi", "Jackson"); }// JDK 8 approach final String capitalNewYork = statesAndCapitals.putIfAbsent("New York", "Albany");在StackOverflow線程Java map.get(key)中討論了在添加putIfAbsent方法之前在Java空間中的替代解決方案–自動(dòng)執(zhí)行put(key)并在key不存在時(shí)返回? 。 值得注意的是,在JDK 8之前, ConcurrentMap接口(擴(kuò)展Map )已經(jīng)提供了putIfAbsent(K,V)方法。
Map.remove(Object,Object)
Map的新刪除(對(duì)象,對(duì)象)方法超出了長(zhǎng)可Map.remove(對(duì)象)方法來(lái)刪除一個(gè)映射條目?jī)H當(dāng)所提供的密鑰,并提供價(jià)值相匹配的地圖(一個(gè)條目以前使用的版本只尋找要?jiǎng)h除的“關(guān)鍵”匹配項(xiàng))。
此方法的Javadoc注釋根據(jù)等效的JDK 8之前的Java代碼說(shuō)明了默認(rèn)方法的實(shí)現(xiàn)方式:
對(duì)于此映射,默認(rèn)實(shí)現(xiàn)等效于:
下一個(gè)代碼清單中顯示了新方法與JDK 8之前方法的具體比較。
/** Demonstrate Map.remove(Object, Object) and compare to pre-JDK 8 approach.* The JDK 8 addition of Map.remove(Object, Object) requires fewer lines of* code than the traditional approach and allows the returned value to be* assigned to a "final" variable.*/// pre-JDK 8 approach boolean removed = false; if ( statesAndCapitals.containsKey("New Mexico")&& Objects.equals(statesAndCapitals.get("New Mexico"), "Sante Fe")) {statesAndCapitals.remove("New Mexico", "Sante Fe");removed = true; }// JDK 8 approach final boolean removedJdk8 = statesAndCapitals.remove("California", "Sacramento");Map.replace(K,V)
兩個(gè)新Map “替換”方法中的第一個(gè)方法僅在指定鍵已經(jīng)存在且具有某些映射值的情況下,將指定值設(shè)置為映射到指定鍵。 Javadoc注釋說(shuō)明了此默認(rèn)方法實(shí)現(xiàn)的Java等效項(xiàng):
對(duì)于此映射,默認(rèn)實(shí)現(xiàn)等效于:
接下來(lái)顯示此新方法與JDK 8之前的方法的比較。
/** Demonstrate Map.replace(K, V) and compare to pre-JDK 8 approach. The JDK 8* addition of replace(K, V) requires fewer lines of code than the traditional* approach and allows the returned value to be assigned to a "final" * variable.*/// pre-JDK 8 approach String replacedCapitalCity; if (statesAndCapitals.containsKey("Alaska")) {replacedCapitalCity = statesAndCapitals.put("Alaska", "Juneau"); }// JDK 8 approach final String replacedJdk8City = statesAndCapitals.replace("Alaska", "Juneau");Map.replace(K,V,V)
第二個(gè)新添加的Map “替換”方法在解釋哪些現(xiàn)有值被替換時(shí)更窄。 盡管剛才介紹的方法將替換映射中可用于指定鍵的值中的任何值,但是這種接受附加( 第三個(gè) )參數(shù)的“替換”方法將僅替換既具有匹配鍵又具有匹配鍵的映射條目的值。匹配值。 Javadoc注釋顯示了默認(rèn)方法的實(shí)現(xiàn):
The default implementation is equivalent to, for this map:if (map.containsKey(key) && Objects.equals(map.get(key), value)) {map.put(key, newValue);return true;} elsereturn false;下一個(gè)代碼清單顯示了我與JDK 8之前的方法的比較。
/** Demonstrate Map.replace(K, V, V) and compare to pre-JDK 8 approach. The* JDK 8 addition of replace(K, V, V) requires fewer lines of code than the* traditional approach and allows the returned value to be assigned to a* "final" variable.*/// pre-JDK 8 approach boolean replaced = false; if ( statesAndCapitals.containsKey("Nevada")&& Objects.equals(statesAndCapitals.get("Nevada"), "Las Vegas")) {statesAndCapitals.put("Nevada", "Carson City");replaced = true; }// JDK 8 approach final boolean replacedJdk8 = statesAndCapitals.replace("Nevada", "Las Vegas", "Carson City");觀察與結(jié)論
從這篇文章中可以得出一些結(jié)論。
- 這些新的JDK 8 Map方法的Javadoc方法非常有用,特別是在描述新方法如何按照J(rèn)DK 8之前的代碼表現(xiàn)時(shí)。 我在有關(guān)基于JDK 8 Javadoc的API文檔的更一般性討論中討論了這些方法的Javadoc。
- 正如這些方法的Javadoc注釋中的等效Java代碼所指示的那樣,這些新方法通常在訪問(wèn)映射鍵和值之前不檢查null。 因此,使用Javadoc注釋中所示的“等效”代碼時(shí),使用這些方法可能會(huì)遇到與null相同的問(wèn)題。 實(shí)際上,Javadoc注釋通常會(huì)警告NullPointerException的可能性,以及與某些Map實(shí)現(xiàn)允許null以及某些鍵和值不允許的問(wèn)題有關(guān)的問(wèn)題。
- 本文中討論的新Map方法是“默認(rèn)方法”,這意味著Map實(shí)現(xiàn)會(huì)自動(dòng)“繼承”這些實(shí)現(xiàn)。
- 本文中討論的新Map方法允許使用更簡(jiǎn)潔的代碼。 在我的大多數(shù)示例中,它們?cè)试S將客戶端代碼從多個(gè)影響狀態(tài)的語(yǔ)句轉(zhuǎn)換為可以一次性設(shè)置局部變量的單個(gè)語(yǔ)句。
這篇文章中介紹的新Map方法并不是開(kāi)創(chuàng)性的或破天荒的,但它們?yōu)樵S多Java開(kāi)發(fā)人員以前實(shí)現(xiàn)了更多詳細(xì)代碼,為其編寫(xiě)了自己的相似方法或?yàn)榈谌綆?kù)提供了便利。 JDK 8將這些標(biāo)準(zhǔn)化方法帶給了Java大眾,而無(wú)需自定義實(shí)現(xiàn)或第三方框架。 由于默認(rèn)方法是實(shí)現(xiàn)機(jī)制,因此即使已經(jīng)存在了很長(zhǎng)時(shí)間的Map實(shí)現(xiàn)也突然并自動(dòng)訪問(wèn)了這些新方法,而無(wú)需對(duì)實(shí)現(xiàn)進(jìn)行任何代碼更改。
翻譯自: https://www.javacodegeeks.com/2014/04/handy-new-map-default-methods-in-jdk-8.html
總結(jié)
以上是生活随笔為你收集整理的JDK 8中方便的新地图默认方法的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 苹果手机进水怎么办
- 下一篇: 苹果手机被人远程控制怎么办