# 表格单元格编辑:保持格式不被破坏 ## 问题 编辑 docx 表格单元格中的文字时,两种常见错误做法都会破坏格式: 1. **`cell.paragraphs[0].clear()` + `add_run()`**:把多段结构压成一段,丢失加粗、字号、字体 2. **XML 层全 cell 文字重分片**:把修改后的文字均匀分配到所有 `w:t` 元素,破坏段落边界和编号 ## 正确做法:段落级精确定位 + 只改目标段 ```python from docx import Document from docx.shared import Pt doc = Document('file.docx') table = doc.tables[0] cell = table.rows[7].cells[1] # 1. 定位目标段落(按索引) paras = cell.paragraphs target_p = paras[4] # 例如 P4 是你要改的段落 # 2. 保存首 run 格式 first_run = target_p.runs[0] saved = { 'name': first_run.font.name, 'size': first_run.font.size, 'bold': first_run.font.bold, 'italic': first_run.font.italic, } # 3. 文字替换 old_text = target_p.text new_text = old_text.replace('要被替换的文字', '新文字') # 4. 清空该段 → 重写(保留格式) target_p.clear() run = target_p.add_run(new_text) run.font.name = saved['name'] run.font.size = saved['size'] run.font.bold = saved['bold'] run.font.italic = saved['italic'] # 5. 合并单元格:同步更新同行其他 cell for col_idx in [2, 3]: cell2 = table.rows[7].cells[col_idx] p = cell2.paragraphs[4] p.clear() run = p.add_run(new_text) run.font.name = saved['name'] run.font.size = saved['size'] doc.save('output.docx') ``` ## 关键原则 - **不碰其他段落**:只改目标索引的段落,其余段落原封不动 - **不压多段为一段**:每个段落独立处理,保持 `P0/P1/P2/P3/P4` 结构不变 - **合并单元格全同步**:`row[7].cells[1]` 改了什么,`cells[2]`、`cells[3]` 也要同步 - **先读后改**:改前用 `cell.paragraphs[i].text` 确认内容,用 `cell.paragraphs[i].runs[0].font` 确认格式 ## 本次教训 2026-06-26 预算绩效分析表:两轮都搞坏格式。 - 第一轮:`clear()` + `add_run()` 把 Row 7 的 P0-P10 多段结构压成一段 - 第二轮:XML 全 cell 文字重分片把 "2.成本核算分析" 变成 ".成本核算分析"(编号丢失) - 第三轮(正确):定位到 P4(成本优化段),只改它,保留 P0-P3 不动