excel单元格行合并

excel单元格行合并

        List<Map<String, String>> compareDatas = new ArrayList<>();
        statisticsSummary.forEach(item -> {
            Map<String, String> data = (Map<String, String>) JSON.parse(JSON.toJSONString(item));
            compareDatas.add(data);
        });
        ExcelUtil.mergeRowsCellContent(sheet, compareDatas, 1, 0, Lists.newArrayList("", "classify"));
/**
     * @param sheet         需要合并的excel
     * @param listData      数据内容
     * @param startRows     需要计算的起始行(数据所在行的下标,下标从0开始算起)
     * @param startCols     需要计算的起始列,从需要比对的字段列开始算起,若是从0开始,且要合并的列不是第一列,则需要在比对字段中使用""占位列数
     * @param compareFields 需要对比的code字段,假如有多个字段需要比对,且不是相邻行的则需要用 "a","","c" 形式,第一列和第三列需要合并,第二列不需要合并
     * @Description: 合并行方法
     * @MethodName: mergeCellContent 
     */
        public static void mergeRowsCellContent(XSSFSheet sheet, List<Map<String, String>> listData, int startRows, int startCols, List<String> compareFields) {
        if (startRows < 1 || CollectionUtils.isEmpty(compareFields) || CollectionUtils.isEmpty(listData)) {
            return;
        }
        // 数据合并计算需要减去 1
        startRows = startRows - 1;
        //备份上一条数据
        Map<String, String> lastDataMap = new HashMap<>();
        //需要合并的行数记录
        Map<String, Integer> mergeRows = new HashMap<>();
        for (int i = 0; i < listData.size(); i++) {
            //当前行数据
            Map<String, String> entity = listData.get(i);
            for (int a = 0; a < compareFields.size(); a++) {
                //首行不做判断合并处理
                if (i == 0) {
                    break;
                }
                //将上下两行同列数据强制转换为字符串进行比较,相同设置单元格合并
                String field = compareFields.get(a);
                if (StringUtils.isEmpty(field)) {
                    continue;
                }
                addMergeRegion(sheet, listData, startRows, startCols, lastDataMap, mergeRows, i, entity, a, field);
            }
            lastDataMap.putAll(entity);
        }
    }

    /**
     * @param sheet
     * @param listData
     * @param startRows
     * @param startCols
     * @param lastDataMap
     * @param mergeRows
     * @param i
     * @param entity
     * @param a
     * @param field
     * @return boolean
     * @Description: 添加单元格合并
     * @MethodName: addMergeRegion 
     */
    private static void addMergeRegion(XSSFSheet sheet, List<Map<String, String>> listData, int startRows, int startCols, Map<String, String> lastDataMap,
        Map<String, Integer> mergeRows, int i, Map<String, String> entity, int a, String field) {
        String lastCode = StringUtils.defaultIfEmpty(lastDataMap.get(field), "");
        String thisCode = StringUtils.defaultIfEmpty(entity.get(field), "");
        String key = a + "###" + field;
        //避免合并判断标识为空,为空
        if (StringUtils.isEmpty(lastCode) || StringUtils.isEmpty(thisCode)) {
            return;
        }
        boolean lastOne = (i == listData.size() - 1);
        //非最后一行的以及上下两行code相同,累加需要合并行数
        if (!lastOne && lastCode.equals(thisCode)) {
            Integer fieldRows = mergeRows.getOrDefault(key, 0);
            fieldRows = fieldRows + 1;
            mergeRows.put(key, fieldRows);
            return;
        }
        //获取需要合并的行数
        Integer fieldRows = mergeRows.getOrDefault(key, 0);
        mergeRows.put(key, 0);
        //不需要合并且不是最后一行,直接跳过
        if (fieldRows == 0 && !lastOne) {
            return;
        }
        //起始行
        int mergeStartRow = (startRows + i - fieldRows);
        //结束行
        int mergeEndRow = (startRows + i);
        //起始列
        int mergeStartCol = (startCols + a);
        //结束列
        int mergeEndCol = (startCols + a);
        //最后一行,且需要和前一行合并,结束行需要+1
        if (lastOne && lastCode.equals(thisCode)) {
            mergeEndRow = mergeEndRow + 1;
        }
        // 最后一行,且不需要和前一行合并,且起始行等于结束行,直接返回
        if (lastOne && !lastCode.equals(thisCode) && mergeStartRow == mergeEndRow) {
            return;
        }
        CellRangeAddress cra = new CellRangeAddress(mergeStartRow, mergeEndRow, mergeStartCol, mergeEndCol);
        try {
            //在sheet里设置合并单元格
            sheet.addMergedRegion(cra);
        } catch (Exception exception) {
            log.error("合并单元格失败:error:", exception);
        }
    }
  • 5
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值