首页 > 解决方案 > 嵌套地图上的流

问题描述

我有以下用例。我有一个具有以下结构的嵌套地图:

Map<String, Map<WorkType, List<CostLineItem>>>

我必须遍历地图并获取 CLObject 列表。如果列表中的单个条目的标识符为空。我必须为每个 EnumType 生成唯一标识符。我不确定如何使用流来做到这一点?遵循迭代逻辑将清楚我想要完成什么

for(Map.Entry<String, Map<WorkType, List<CostLineItem>>> cliByWorkTypeIterator: clisByWorkType.entrySet()) {
       Map<WorkType, List<CostLineItem>> entryValue = cliByWorkTypeIterator.getValue();
       for(Map.Entry<WorkType, List<CostLineItem>>cliListIterator : entryValue.entrySet()) {
           List<CostLineItem> clis = cliListIterator.getValue();
           //if any CLI settlementNumber is zero this means we are in standard upload
           //TODO: Should we use documentType here? Revisit this check while doing dispute file upload
           if(clis.get(0).getSettlementNumber() == null) {
               clis.forEach(f -> f.toBuilder().settlementNumber(UUID.randomUUID().toString()).build());
           }
       }
   } 

嵌套循环使代码位样板和肮脏。有人可以帮我处理这里的流吗?

标签: javajava-8hashmapjava-stream

解决方案


您可以使用flatMap迭代List<CostLineItem>所有内部Maps 的所有值。

clisByWorkType.values() // returns Collection<Map<WorkType, List<CostLineItem>>>
              .stream() // returns Stream<Map<WorkType, List<CostLineItem>>>
              .flatMap(v->v.values().stream()) // returns Stream<List<CostLineItem>>
              .filter(clis -> clis.get(0).getSettlementNumber() == null) // filters that Stream
              .forEach(clis -> {do whatever logic you need to perform on the List<CostLineItem>});

推荐阅读