使用Google Guava创建收藏和实现不变性
因此,我想看看番石榴提供的一些集合創建模式,以及它提供的某些不可變集合類型。
如果您沒有看過我以前的文章,則可能要從這里開始:
番石榴第1部分– MultiMaps
番石榴第2部分– BiMaps
番石榴第3部分–多組
Guava的所有集合實現都包含一個或多個靜態create方法,這些方法可以實現您所期望的,并且通常提供一種更為簡潔的實例化集合類的方法。 這是創建ArrayListMultimap的兩種不同方法
Multimap<String,String> multimap1 = new ArrayListMultimap<String,String>();Multimap<String,String> multimap2 = ArrayListMultimap.create();好的,因此其中沒有太多內容(在此示例中為12個字符),但是從我的角度來看,您正在刪除一些冗余,我們真的需要兩次重現泛型類型信息嗎?
很好,很遺憾,Sun沒想到在創建Java 5時向其Collection類型添加create方法!
同樣,番石榴在這里為您提供幫助,并提供了一些用于處理標準集合類型的實用程序類。 com.google.common.collect.Lists , com.google.common.collect.Sets和com.google.common.collect.Maps
這些都提供了幾種格式為new CollectionType () ,下面是一些示例
List<String> myList1 = new ArrayList<String>(); //old wayList<String> myList2 = Lists.newArrayList(); //guava waySet<String> mySet1 = new HashSet<String>(); //old waySet<String> mySet2 = Sets.newHashSet(); //guava way由于“ new”方法是靜態的,因此您可以通過使用靜態導入來剪切出更多字符,即…
import static com.google.common.collect.Lists.newArrayList;import static com.google.common.collect.Sets.newHashSet;//elsewhere in codeList<String> myList2 = newArrayList();Set<String> mySet2 = newHashSet();明智的按鍵方式是,使用番石榴方法并不能真正節省很多,所以我想這和其他任何東西都一樣。 我個人認為,番石榴的方法讀起來要好得多,盡管我認為我不會使用靜態導入。
到目前為止,還不錯,但是幾乎沒有崩潰的余地,下一步呢?
不變的收藏
這些本質上是集合對象,創建后就無法更改,并且出于各種原因很有用。 Guava為大多數常規Collection接口提供了Immutable實現: ImmutableList , ImmutableSet和ImmutableMap ,以及某些Guava集合接口( ImmutableMultimap等)的不可變實現。
我對它們的主要用途是創建靜態常量。 例如,假設您出于某種目的需要對一組字符串進行硬編碼。
一種做到這一點的方法可能是,例如。
它看起來并不好看,并且存在一個主要問題。 任何可以訪問此Set的代碼都可以對其進行更改,這可能導致各種意外問題。
我們不能只使用Collection.unmodifiableSet(Set s)來解決這個問題嗎?
好吧,在這個特定的例子中,我想我們可以寫……
private static final Set<String> farmAnimals =Collections.unmodifiableSet(new HashSet<String>(Arrays.asList('Cow','Pig','Sheep')));…但是這開始顯得有些笨拙,而且無法unmodifiable方法還有另一個問題。 它們僅返回集合的不可修改視圖,如果您引用原始集合,則仍然可以對其進行更改!
盡管在上一個示例中這可能不是問題,但我仍然認為更好的方法是使用ImmutableSet
private static final Set<String> farmAnimals = ImmutableSet.of('Cow','Pig','Sheep');是不是更好呢! 還有其他幾種創建它們的方法,下面是一些示例:
// use copyOf()...public void doStuffWithList(List<Object> unsafeList) {List<Object> safeList = ImmutableList.copyOf(unsafeList);}// use a builder...public Map<String,Integer> makeImmutableMap() {ImmutableMap.Builder<String,Integer> mapBuilder = new ImmutableMap.Builder<String,Integer>();Entry<String,Integer> entry = null;while((entry = getEntry()) != null) {mapBuilder.put(entry.getKey(), entry.getValue());}return builder.build();}那么,使用不可變集合還有其他優勢嗎?
好吧,有幾個。 它們可以大大簡化邏輯,尤其是在多線程環境中。 如果線程僅具有對對象的讀取訪問權限,則您無需擔心復雜的線程同步邏輯
創建它們后,它們的使用效率也略有提高。 如果一個集合事先知道它需要存儲什么,并且永遠不會有任何變化,則可以節省各種時間和空間。 例如,大多數ArrayLists或HashMaps的實現都會為新對象保留一些未使用的空間,因此它們不必不斷調整自身大小。 如果您知道永遠不會有任何新對象,則無需這樣做。
最后,您還可以將它們用作哈希鍵。 如果集合的內容無法更改,那么它的哈希碼也不會改變!
有什么缺點嗎?
當然,不可變對象有一個很大的缺點,那就是顯而易見的。 您不能更改它們! 如果您需要更改集合,則首先需要對其進行復制。 在某些情況下(例如,并發性很重要),您實際上可能希望采用這種方法。 但是,在集合包含許多對象的情況下,這將是不切實際的,并且您可能需要一個老式的可變集合(如果需要,請完成同步代碼)。
唯一需要注意的另一件事是,僅僅因為您的集合是不可變的,并不意味著它們中包含的對象是自動的。 如果可以在不可變集合中獲得對對象的引用,那么沒有什么可以阻止您更改該對象上的任何可變狀態! 因此,最佳實踐是確保您保存在不可變集合中的任何東西本身都是不可變的!
參考: Tom's Programming Blog博客上的JCG合作伙伴 Tom Jefferys從Google Guava創建的收藏和不變性 。
翻譯自: https://www.javacodegeeks.com/2012/12/collection-creation-and-immutability-with-google-guava.html
總結
以上是生活随笔為你收集整理的使用Google Guava创建收藏和实现不变性的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 绝地求生最新画面设置(绝地求生最新游戏画
- 下一篇: 均衡器怎么调能达到最佳效果