Java 8 Streams分组归约后将BigDecimal转为格式化货币字符串的方法
问题结论
可以直接对分组归约后的结果进行映射处理,有两种可选实现方式,可根据是否需要保留原始BigDecimal类型的统计金额选择。
方案1:流归集阶段一步完成(仅遍历一次,性能最优)
直接修改原来的collect逻辑,借助Collectors.collectingAndThen对归约得到的BigDecimal结果直接做格式化,不需要额外二次处理Map:
Map<String, String> itemTypesAndCosts = items.stream().collect(Collectors.groupingBy( Item::getType, Collectors.collectingAndThen( Collectors.reducing(BigDecimal.ZERO, Item::getCost, BigDecimal::add), total -> String.format("\"$%s\"", total) ) ));
直接输出itemTypesAndCosts就能得到目标格式{Food="$9.00", Toy="$6.00"}。
方案2:先保留原始统计值再做映射(适合需要后续金额计算的场景)
如果业务逻辑后续还需要用到BigDecimal类型的总金额做运算,可以先拿到原始统计Map,再单独做值转换:
// 原有逻辑保留,得到BigDecimal类型的统计结果 Map<String, BigDecimal> itemTypesAndCosts = items.stream().collect(Collectors.groupingBy(Item::getType, Collectors.reducing(BigDecimal.ZERO, Item::getCost, BigDecimal::add))); // 单独做值映射得到格式化后的Map Map<String, String> formattedResult = itemTypesAndCosts.entrySet().stream() .collect(Collectors.toMap( Map.Entry::getKey, entry -> String.format("\"$%s\"", entry.getValue()) ));
输出formattedResult即可得到目标格式,同时itemTypesAndCosts还可以继续用于其他金额计算逻辑。
内容的提问来源于stack exchange,提问作者Dynamic
相关产品推荐
相关产品推荐

