因为的美国的制裁,加速了国内不少公司产品构成去美化进程,而在软件行业的数据库层面,愈来愈多的公司进行去Oracle化。本人所在公司有自研内存数据库,聚合函数的支持初期没那么完善,有时一部分逻辑要从数据库转化到java实现,今天举一个java实现分组求和来代替数据库聚合函数sum()+group by的栗子java
举一个生产过程的引用例子,代码以下:数据库
/** * @Description //TODO 根据客户列表查欠费信息 * @Date: 2021/7/15 **/ public List<UnPayBillDTO> getUnPayInfo(List<Long> contractNoList,String yearMonth){ List<UnPayBillDTO> unPayBillDTOList = new ArrayList<>(); // 结果集 for (long contractNo : contractNoList) { ActUnpayoweInfo actUnpayoweInfoParam = new ActUnpayoweInfo(); actUnpayoweInfoParam.setContractNo(contractNo); List<ActUnpayoweInfo> actUnpayoweInfos = actUnpayoweInfoMapper.select(actUnpayoweInfoParam); // 该帐户全部欠费信息 /* 分组 */ Map<String,List<ActUnpayoweInfo>> afterGroupMap = actUnpayoweInfos.stream(). filter(o -> o.getNaturalMonth().equals(yearMonth)). // 过滤掉当月欠费 collect(Collectors.groupingBy(o -> o.getContractNo() + "_" + o.getNaturalMonth() + "_" + o.getAcctItemCode())); afterGroupMap.forEach( (group, groupInfo) -> { /* 获取分组字段 */ String[] tmpInfo = group.split("_"); long tmpContractNo = Long.parseLong(tmpInfo[0]); String tmpNaturalMonth = tmpInfo[1]; String tmpAcctItemCode = tmpInfo[2]; /* 求和 */ long totalMoney = groupInfo.stream().mapToLong(this::calculate).sum(); UnPayBillDTO unPayBillDTO = new UnPayBillDTO(); unPayBillDTO.setContractNo(tmpContractNo); unPayBillDTO.setNaturalMonht(tmpNaturalMonth); unPayBillDTO.setAcctItemCode(tmpAcctItemCode); unPayBillDTO.setTotalMoney(totalMoney); unPayBillDTOList.add(unPayBillDTO); } ); } return unPayBillDTOList; }
分组是先利用stream进行遍历,而后以group by涉及的字段进行拼接,做为Collector进行分组的条件,最终返回一个以分组条件拼接的字符串做为key值,分好组的各个对应list做为value的map;app
Map<String,List<ActUnpayoweInfo>> afterGroupMap = actUnpayoweInfos.stream(). filter(o -> o.getNaturalMonth().equals(yearMonth)). // 过滤掉当月欠费 collect(Collectors.groupingBy(o -> o.getContractNo() + "_" + o.getNaturalMonth() + "_" + o.getAcctItemCode()));
对每一组进行处理,从key值获取分组条件信息,对value值里面的多条数据相关字段进行计算后累加求和函数
/* 获取分组字段 */ String[] tmpInfo = group.split("_"); long tmpContractNo = Long.parseLong(tmpInfo[0]); String tmpNaturalMonth = tmpInfo[1]; String tmpAcctItemCode = tmpInfo[2]; /* 求和 */ long totalMoney = groupInfo.stream().mapToLong(this::calculate).sum();
this::calculate
是涉及业务的一些计算,这里不作展开this