поток создает дополнительный список - как избежать - PullRequest
0 голосов
/ 30 августа 2018

У меня проблема с поиском правильного способа потоковой передачи и сбора моих данных.

Поток следующий

  public List<List<CalculatedItemCostPerStore>> getCalcualtedItemCostPerStore() {
    var it = item
        .getQuantities().stream().map(quantities -> {
          Store.StoreCosts<CostType, BigDecimal> storeCosts = quantities.getStore().getStoreCosts();
          return new CalculatedItemCostPerStore(quantities.getStore().getName(), new TreeSet<>(quantities
              .getItemCostEvents()
              .stream()
              .map(e -> new CalculatedItemCost(e.getCostTrigger(), e.getTriggerQuantity().multiply(storeCosts.get(e.getCostTrigger()))))
              .collect(
                  Collectors.toMap(CalculatedItemCost::getCostType, Function.identity(), (a, b) -> new CalculatedItemCost(a.getCostType(), a.getCost().add(b.getCost())))
              ).values()));
        }).collect(Collectors.groupingBy(CalculatedItemCostPerStore::getStore)).values().stream().collect(Collectors.toList());
    return it;
  }

Получить потоком в

  @Data
  @AllArgsConstructor
  static class CalculatedItemCost implements Comparable<CalculatedItemCost> {
    private CostType costType;
    private BigDecimal cost;

    @Override
    public int compareTo(CalculatedItemCost o) {
      return this.costType.toString().compareTo(o.getCostType().toString());
    }
  }

  @Data
  @AllArgsConstructor
  static class CalculatedItemCostPerStore {
    private String store;
    private TreeSet<CalculatedItemCost> calculatedItemCosts;
  }

и itemCostEvents - это список

{
  "createdAt": "2018-08-29T00:00:00",
  "costTrigger": "STORAGE_COST_PER_CBM_PER_DAY",
  "triggerQuantity": 33
}

выше потока создает результат, который представлен ниже json. Как вы можете видеть это List<List<CalculatedItemCostPerStore>>

"calcualtedItemCostPerStore": [
    [
      {
        "store": "foo",
        "calculatedItemCosts": [
          {
            "costType": "ADDITIONAL_COST_OFFICE_PER_HOUR",
            "cost": 1368
          },
          {
            "costType": "STORAGE_COST_PER_CBM_PER_DAY",
            "cost": 287.1
          }
        ]
      }
    ],
    [
      {
        "store": "bar",
        "calculatedItemCosts": [
          {
            "costType": "ADDITIONAL_COST_OFFICE_PER_HOUR",
            "cost": 38
          }
        ]
      }
    ]
  ]

Может быть любое количество экземпляров количеств, каждое из которых может иметь один магазин.

Я хотел бы получить один List<CalculatedItemCostPerShop>, как показано ниже

"calcualtedItemCostPerStore": [
    {
        "store": "foo",
        "calculatedItemCosts": [
            {
                "costType": "ADDITIONAL_COST_OFFICE_PER_HOUR",
                "cost": 1368
            },
            {
                "costType": "STORAGE_COST_PER_CBM_PER_DAY",
                "cost": 287.1
            }
        ]
    },
    {
        "store": "bar",
        "calculatedItemCosts": [
            {
                "costType": "ADDITIONAL_COST_OFFICE_PER_HOUR",
                "cost": 38
            }
        ]
    }
 ]

Как мне нужно настроить поток, чтобы получить результат выше?

1 Ответ

0 голосов
/ 30 августа 2018

Решил это благодаря @ernest_k - используя flatMap на .values()

public List<CalculatedItemCostPerStore> getCalcualtedItemCostPerStore() {
    return item
        .getQuantities().stream().map(quantities -> {
          Store.StoreCosts<CostType, BigDecimal> storeCosts = quantities.getStore().getStoreCosts();
          return new CalculatedItemCostPerStore(quantities.getStore().getName(), new TreeSet<>(quantities
              .getItemCostEvents()
              .stream()
              .map(e -> new CalculatedItemCost(e.getCostTrigger(), e.getTriggerQuantity().multiply(storeCosts.get(e.getCostTrigger()))))
              .collect(
                  Collectors.toMap(CalculatedItemCost::getCostType, Function.identity(), (a, b) -> new CalculatedItemCost(a.getCostType(), a.getCost().add(b.getCost())))
              ).values()));
        })
        .collect(Collectors.groupingBy(CalculatedItemCostPerStore::getStore))
        .values()
        .stream()
        .flatMap(Collection::stream).collect(Collectors.toList())
        ;
  }
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...