首页 > 解决方案 > Hashmap - 按月分组

问题描述

显示类别日期并需要根据每个类别的日期和总金额对它们进行分组的项目列表。我该怎么做?

我的java代码:

final Map<String, TemporalAdjuster> ADJUSTERS = new HashMap<>();
ADJUSTERS.put("day", TemporalAdjusters.ofDateAdjuster(d -> d)); // identity
ADJUSTERS.put("week", TemporalAdjusters.previousOrSame(DayOfWeek.of(1)));
ADJUSTERS.put("month", TemporalAdjusters.firstDayOfMonth());
ADJUSTERS.put("year", TemporalAdjusters.firstDayOfYear());

Map <LocalDate, List<Data>> TotalVal = ldata
        .stream()
        .sorted(Comparator
                .comparingInt(Data::getAmount)
                .reversed()
        )
        .collect(Collectors
                .groupingBy(item -> item.getDate().with(ADJUSTERS.get("month")))
                .collect(Collectors
                        .toMap(Data::getName, 
                                Data::getAmount, 
                                (sumAmt, amt) -> sumAmt + amt, 
                                LinkedHashMap::new)
                )
        );

我的输入为 json:

Statement: [
  {
    "date": "12-09-19",
    "Category": "Bills",
    "Amount": "100"
  },
  {
    "date": "11-09-19",
    "Category": "Grocery",
    "Amount": "1010"
  },
  {
    "date": "21-08-19",
    "Category": "Other Household Bills",
    "Amount": "1320"
  },
  {
    "date": "11-08-19",
    "Category": "Service",
    ,
    "Amount": "2100"
  },
  {
    "date": "11-09-19",
    "Category": "Food & Dining Out",
    "Amount": "1010"
  },
  {
    "date": "21-08-19",
    "Category": "Service",
    "Amount": "100"
  },
  {
    "date": "18-09-19",
    "Category": "Bills",
    "Amount": "100"
  }
]

我的预期输出:

9 月 19 日杂货:1010,外出就餐:1010,账单:200 8 月 19 日服务:2200,其他家庭账单:1320

标签: javajava-8hashmapjava-stream

解决方案


首先按月-年分组,然后按类别分组。

public class Main {

  public static void main(String[] args) {
    List<Data> data = List.of(
        new Data(LocalDate.of(2019, 9, 12), "Bills", 100),
        new Data(LocalDate.of(2019, 9, 11), "Grocery", 1010),
        new Data(LocalDate.of(2019, 8, 21), "Other Household Bills", 1320),
        new Data(LocalDate.of(2019, 8, 11), "Service", 2100),
        new Data(LocalDate.of(2019, 8, 21), "Food & Dining Out", 1010),
        new Data(LocalDate.of(2019, 9, 18), "Bills", 100)
    );

    var result = data.stream()
        .collect(Collectors.groupingBy(
            data1 -> data1.getDate().getMonth()+"-"+ data1.getDate().getYear(),
            Collectors.groupingBy(Data::getCategory, Collectors.summingInt(Data::getAmount))
        ));

    result.forEach((localDate, stringIntegerMap) -> {
      System.out.print(localDate +" ");
      stringIntegerMap.forEach((s, integer) -> System.out.print(s + " :" + integer+" "));
      System.out.println();

    });
  }

}

class Data {

  private LocalDate date;
  private String category;
  private int amount;

  public Data(LocalDate date, String category, int amount) {
    this.date = date;
    this.category = category;
    this.amount = amount;
  }
  //getters & setters
}


推荐阅读