Openpyxl写入DataFrame时如何合并列内连续相同单元格
DataFrame导出Excel合并连续同值单元格实现方案
核心逻辑不依赖pandas ExcelWriter的内置封装,直接基于Excel操作引擎识别连续同值区间后执行合并,兼容性更强,可灵活指定需要合并的列。
实现步骤
- 先将DataFrame按常规流程无格式写入Excel文件
- 针对指定待合并的列,逐行扫描定位所有值相同的连续行区间
- 对长度大于1的连续区间调用引擎的合并API完成单元格合并,可按需追加对齐、边框等格式设置
可直接复用的代码(基于openpyxl引擎,无额外依赖)
import pandas as pd from openpyxl import load_workbook def merge_continuous_cells(df: pd.DataFrame, output_path: str, merge_cols: list = None): # 默认表头在第1行,数据从第2行开始 HEADER_ROW = 1 # 先写入原始数据 with pd.ExcelWriter(output_path, engine='openpyxl') as writer: df.to_excel(writer, index=False) wb = load_workbook(output_path) ws = wb.active # 未指定列时默认合并所有列 if not merge_cols: merge_cols = df.columns.tolist() for col in merge_cols: col_idx = df.columns.get_loc(col) + 1 # openpyxl列号从1开始 block_start_row = HEADER_ROW + 1 block_val = None for row in range(HEADER_ROW + 1, ws.max_row + 1): current_val = ws.cell(row=row, column=col_idx).value if block_val is None: block_val = current_val continue # 遇到不同值时处理前一个连续块 if current_val != block_val: if row - block_start_row > 1: ws.merge_cells( start_row=block_start_row, start_column=col_idx, end_row=row-1, end_column=col_idx ) block_start_row = row block_val = current_val # 处理最后一个未收尾的连续块 if ws.max_row - block_start_row >= 1: ws.merge_cells( start_row=block_start_row, start_column=col_idx, end_row=ws.max_row, end_column=col_idx ) wb.save(output_path) # 调用示例 if __name__ == "__main__": test_df = pd.DataFrame({ "部门": ["技术部", "技术部", "技术部", "产品部", "产品部", "运营部"], "姓名": ["张三", "李四", "王五", "赵六", "钱七", "孙八"], "绩效等级": ["A", "A", "B", "A", "B", "B"] }) # 按需传入要合并的列即可 merge_continuous_cells(test_df, "导出结果.xlsx", merge_cols=["部门", "绩效等级"])
补充说明
- 如果使用xlsxwriter作为写入引擎,逻辑完全一致,仅需将合并API替换为
ws.merge_range(),注意xlsxwriter不支持文件写入后再加载修改,需要把区间识别、合并逻辑嵌入到写入流程中同步执行 - 合并后的单元格默认继承区域左上角单元格的样式,需要调整对齐、边框、字体的话,直接设置左上角单元格的样式即可,不需要给整个区域重复赋值
- 该方案不会修改原始DataFrame的结构,所有合并操作仅作用于最终导出的Excel文件

内容的提问来源于stack exchange,提问作者chicagobeast12
相关产品推荐
相关产品推荐

