java代碼之美(6)---guava之multimap


guava之multimap

上一篇講到Multiset它可以對存入相同元素做一個計數的功能,那multimap呢?

一、概述

1、基本介紹和案例說明

multimap和MultiSet的繼承結果很相似,只不過在上層的接口是Multimap不是Multiset。

Multimap的特點其實就是可以包含有幾個重復Key的value,你可以put進入多個不同value但是相同的key,但是又不是讓后面覆蓋前面的內容。

它的業務場景:當你需要構造像Map<K, List<V>>或者Map<K, Set<V>>這樣比較復雜的集合類型的數據結構,來做相應的業務邏輯處理。那Multimap在合適不過。

舉例

        @Test
        public void testMultimap(){
        HashMultimap<Integer, Integer> map = HashMultimap.create();
        map.put(1, 2);
        map.put(1, 3);
        map.put(1, 2);
        map.put(2, 3);
        map.put(4, 2);
        map.put(4, 3);
        map.put(4, 2);
        map.put(4, 3);
        System.out.println(map.toString());
    }
}
/*輸出結果:
 *{1=[2, 3], 2=[3], 4=[2, 3]}
 */

其實它會把相同key和value的值給覆蓋起來,但是相同的key又可以保留不同的value。因為它的entry的實現是一個set,set會對相同的Entry<K,V>進行去重,所以會有這種情況。 

2、實際開發場景及常用方法

 (1)根據業務需要對下面的list數據根據name字段來進行分組:

[
    {
        "date":"2018-01-31",
        "name":"wuzhong",
        "socre":0.8
    },
    {
        "date":"2018-01-30",
        "name":"wuzhong",
        "socre":0.9
    },
    {
        "date":"2018-01-31",
        "name":"wuzhong2",
        "socre":0.8
    }
]

傳統做法

//Item就是封裝的對象
Map<String,List<Item>> map = new HashMap<>();
for (Item item : list){
  List<Item> tmp = map.get(item.getName());
  if (null == tmp){
      tmp = new ArrayList<>();
      map.put(item.getName(),tmp);
  }
  tmp.add(item);
}

很簡單, 但是代碼量有點多,特別是需要判斷List為null並初始化。

再用guava實現上述的功能:

Multimap<String,Item> multiMap = ArrayListMultimap.create();
for (Item item : list){
    multiMap.put(item.getName(),item);
}

代碼量直接減少了一半,這就是實際開發中它發揮的作用。

(2)再舉一例子了解常用方法

public class MultimapTest {


        public static void main(String args[]){

              Multimap<String,String> multimap = ArrayListMultimap.create();

            multimap.put("lower", "a");
            multimap.put("lower", "b");
            multimap.put("lower", "c");

            multimap.put("upper", "A");
            multimap.put("upper", "B");

            List<String> lowerList = (List<String>)multimap.get("lower");
            //輸出key為lower的list集合
            System.out.println("輸出key為lower的list集合=========");
            System.out.println(lowerList.toString());
            lowerList.add("f");
            System.out.println(lowerList.toString());


            Map<String, Collection<String>> map = multimap.asMap();
            System.out.println("把Multimap轉為一個map============");
            for (Map.Entry<String,  Collection<String>> entry : map.entrySet()) {
                String key = entry.getKey();
                Collection<String> value =  multimap.get(key);
                System.out.println(key + ":" + value);
            }

            System.out.println("獲得所有Multimap的key值==========");
            Set<String> keys =  multimap.keySet();
            for(String key:keys){
                System.out.println(key);
            }

            System.out.println("輸出Multimap所有的value值========");
            Collection<String> values = multimap.values();
            System.out.println(values);
        }
}
/**輸出結果:
 *輸出key為lower的list集合=========
 * [a, b, c]
 * [a, b, c, f]
 * 把Multimap轉為一個map============
 * lower:[a, b, c, f]
 * upper:[A, B]
 * 獲得所有Multimap的key值==========
 * lower
 * upper
 * 輸出Multimap所有的value值========
 * [a, b, c, f, A, B]
  */

4、Multimap的實現類

  Multimap提供了豐富的實現,所以你可以用它來替代程序里的Map<K, Collection<V>>,具體的實現如下:

   Implementation            Keys 的行為類似          Values的行為類似

  ArrayListMultimap         HashMap                     ArrayList

  HashMultimap               HashMap                     HashSet

  LinkedListMultimap        LinkedHashMap*              LinkedList*

  LinkedHashMultimap      LinkedHashMap                LinkedHashSet

  TreeMultimap                TreeMap                          TreeSet

  ImmutableListMultimap  ImmutableMap                 ImmutableList

  ImmutableSetMultimap  ImmutableMap                 ImmutableSet  

  以上這些實現,除了immutable的實現都支持null的鍵和值。

  1、LinkedListMultimap.entries()能維持迭代時的順序。

  2、LinkedHashMultimap維持插入的順序,以及鍵的插入順序。

 

參考

 1、Guava新增集合類型-Multimap

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM