2017-03-04 41 views
2

我想轉換一個Map<String, List<MyObject>> to List<Map<String, MyObject>>轉換地圖<字符串,列表<MyObject>爲List <地圖<字符串,爲MyObject >>在Java中

{<key1,[myObject1, myObject2]>, <key2,[myObject3, myObject4]>} will be converted to [{<key1,myObject1>, <key2,myObject3>}, {<key1,myObject2>, <key2, myObject4>}]

其中myObject1和myObject3具有相同的唯一的ID等做myObject2和myObject4。

我的實現在下面,但有沒有更好的方式來做到這一點。

private List<Map<String, MyObject>> getObjectMapList(Map<String, List<MyObject>> objectMap) 

{ 
    List<Map<String, MyObject>> objectMapList = new ArrayList<Map<String,MyObject>>(); 

for(MyObject myObject : objectMap.get("key1")) {// there will be default key1 whose value is known 

     Map<String, MyObject> newMap= new HashMap<String, MyObject>(); 
     for (String key : objectMap.keySet()) { 
      newMap.put(key, objectMap.get(key).stream() 
        .filter(thisObject -> thisObject.getId().equals(myObject.getId())) 
        .collect(Collectors.toList()).get(0)); 
     } 
     objectMapList.add(newMap); 
    } 
    return objectMapList; 

} 
+0

哪裏了'language'變量從何而來? – Jeff

+0

是一些錯字。編輯它 – user3330263

回答

0

此流應該返回您想要的結果。使用舊的Eclipse版本時,我遇到了一些類型問題。你可能不得不把它分解成單個步驟,或者在lambdas中添加一些類型,但我想保持簡短。

Map<String, List<MyObject>> objectMap = new HashMap<>(); 

objectMap.keySet() 
     .stream() 
     .flatMap(key -> objectMap.get(key) 
            .stream() 
            .map(obj -> new AbstractMap.SimpleEntry<>(key, obj))) 
     .collect(groupingBy(pair -> pair.getValue().getId())) 
     .values() 
     .stream() 
     .map(listOfSameIds -> listOfSameIds.stream() 
              .collect(toMap(SimpleEntry::getKey, SimpleEntry::getValue))) 
     .collect(toList()); 

我要做的就是:

  1. 對所有與他們的鑰匙所有輸入的值對象,並把它們放在一個長長的清單(flatMap(key -> streamOfKeyObjectPairs))。
  2. 通過對象的ID(collect(groupingBy))將這些對分開。
  3. 取各基團和對的列表轉換成地圖(map(list -> toMap)
  4. 把所有這些地圖到一個列表
+0

我無法得到它的工作。 groupingBy(pair-> pair.getValue()。getId())如果分割進入不同的操作,則會抱怨未知對象事件 – user3330263

+0

您是否爲groupingBy方法添加了導入?編寫'Collectors.groupingBy'來檢查導入是否丟失。否則,可以嘗試通過用((SimpleEntry pair) - > pair.getValue()。getId()來替換'pair - > pair.getValue()。getId()'來明確地輸入'pair'參數。 )'。如果仍然不起作用,你可以嘗試將lambda賦值給一個Function變量:'Function ,ID_TYPE> toID = pair - > pair.getValue()。getId()'。 –

1

這裏有一個1班輪沒有任何大括號:

private List<Map<String, MyObject>> getObjectMapList(Map<String, List<MyObject>> objectMap) { 
    return map.entrySet().stream() 
     .map(e -> e.getValue().stream() 
     .map(o -> Collections.singletonMap(e.getKey(), o)) 
     .collect(Collections.toList()) 
    .flatMap(List::stream) 
    .collect(Collections.toList()); 
} 

這裏的主要「技巧」是使用Collections.singletonMap()來允許地圖的無塊嵌入式創建和填充。


免責聲明:代碼可能無法編譯或工作,因爲它是在翻閱我的手機上(但有一個合理的機會,將工作)

+0

看起來不錯,我會記住'singletonMap'。但是這是否仍然通過'MyObject.getId()'對這些對進行分組?或者結果列表中的每個地圖是否只包含一個映射? –

+0

@MalteHartwig只有一個映射 – Bohemian

相關問題