Java 8 - Optional实战
文章目錄
- Pre
- 用 Optional 封裝可能為 null 的值
- 異常與 Optional 的對比
- 避免使用基本類型的Optional對象
Pre
Java 8 - Optional全解相信你已經了解,有效地使用 Optional 類意味著你需要對如何處理存在缺失值進行全面的反思。這種反思不僅僅限于你曾經寫過的代碼,更重要的可能是,你如何與原生Java API實現共存共贏。
實際上,我們相信如果 Optional 類能夠在這些API創建之初就存在的話,很多API的設計編寫可能會大有不同。為了保持后向兼容性,我們很難對老的Java API進行改動,讓它們也使用Optional ,但這并不表示我們什么也做不了。你可以在自己的代碼中添加一些工具方法,修復或者繞過這些問題,讓你的代碼能享受 Optional 帶來的威力。
接下來我們會通過幾個實際的例子講解如何達到這樣的目的
用 Optional 封裝可能為 null 的值
現存Java API幾乎都是通過返回一個 null 的方式來表示需要值的缺失,或者由于某些原因計算無法得到該值。比如,如果 Map 中不含指定的鍵對應的值,它的 get 方法會返回一個 null 。但是,正如我們之前介紹的,大多數情況下,你可能希望這些方法能返回一個 Optional 對象。你無法修改這些方法的簽名,但是你很容易用 Optional 對這些方法的返回值進行封裝裝。
我們接著用 Map 做例子,假設你有一個 Map<String, Object> 方法,訪問由 key 索引的值時,如果 map中沒有與 key 關聯的值,該次調用就會返回一個 null 。
Object value = map.get("key");使用 Optional 封裝 map 的返回值,你可以對這段代碼進行優化。要達到這個目的有兩種方式:
- 你可以使用笨拙的 if-then-else 判斷語句,毫無疑問這種方式會增加代碼的復雜度;
- 或者你可以采用我們前文介紹的 Optional.ofNullable 方法
每次你希望安全地對潛在為 null 的對象進行轉換,將其替換為 Optional 對象時,都可以考慮使用這種方法。
異常與 Optional 的對比
由于某種原因,函數無法返回某個值,這時除了返回 null ,Java API比較常見的替代做法是拋出一個異常。、
這種情況比較典型的例子是使用靜態方法 Integer.parseInt(String) ,將String 轉換為 int 。在這個例子中,如果 String 無法解析到對應的整型,該方法就拋出一個NumberFormatException 。
最后的效果是,發生 String 無法轉換為 int 時,代碼發出一個遭遇非法參數的信號,唯一的不同是,這次你需要使用 try / catch 語句,而不是使用 if 條件判斷來控制一個變量的值是否非空。
你也可以用空的 Optional 對象,對?遇無法轉換的 String 時返回的非法值進行建模,這時你期望 parseInt 的返回值是一個 optional 。我們無法修改最初的Java方法,但是這無礙我們進行需要的改進,你可以實現一個工具方法,將這部分邏輯?裝于其中,最終返回一個我們希望的Optional 對象。
【將 String 轉換為 Integer ,并返回一個 Optional 對象】
我們的建議是,你可以將多個類似的方法?裝到一個工具類中,讓我們稱之為 Optiona-lUtility 。通過這種方式,你以后就能直接調用 OptionalUtility.stringToInt 方法,將String 轉換為一個 Optional<Integer> 對象。
避免使用基本類型的Optional對象
與 Stream 對象一樣, Optional 也提供了類似的基礎類型—— OptionalInt 、 OptionalLong 以及 OptionalDouble .
比如上面的方法可以不返回 Optional<Integer> ,而是直接返回一個 OptionalInt 類型的對象。 我們討論過使用基礎類型 Stream 的場景,尤其是如果 Stream 對象包含了大量元素,出于性能的考量,使用基礎類型是不錯的選擇,但對 Optional 對象而言,這個理由就不成立了,因為 Optional對象最多只包含一個值。
不推薦使用基礎類型的 Optional ,因為基礎類型的 Optional 不支持 map 、flatMap 以及 filter 方法,而這些卻是 Optional 類最有用的方法。
此外,與 Stream 一樣, Optional 對象無法由基礎類型的 Optional 組合構成,所以,舉例而言,如果上面的代碼中返回的是 OptionalInt 類型的對象,你就不能將其作為方法引用傳遞給另一個 Optional 對象的 flatMap 方法。
總結
以上是生活随笔為你收集整理的Java 8 - Optional实战的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Java 8 - Completable
- 下一篇: Java 8 - 收集器Collecto