Python教学基础:用Python和openpyxl结合Word模板域写入数据-由Deepseek产生

使用Python和openpyxl结合Word模板域写入数据

在Python中,我们可以使用openpyxl处理Excel数据,然后结合Word模板中的域(书签或合并域)来生成定制化的Word文档。以下是几种实现方法:

方法一:使用书签(Bookmarks)

1. 准备Word模板

首先创建一个Word模板,在需要插入数据的位置添加书签。

2. Python实现代码

python 复制代码
import openpyxl
from docx import Document
from docx.shared import Inches

def fill_word_template_from_excel(excel_file, word_template, output_file):
    # 读取Excel数据
    wb = openpyxl.load_workbook(excel_file)
    ws = wb.active
    
    # 读取Word模板
    doc = Document(word_template)
    
    # 假设Excel第一行是标题,第二行是数据
    data = {}
    for i, cell in enumerate(ws[1], 1):
        data[cell.value] = ws[2][i-1].value
    
    # 替换Word中的书签
    for paragraph in doc.paragraphs:
        for key, value in data.items():
            if key in paragraph.text:
                paragraph.text = paragraph.text.replace(f'[{key}]', str(value))
    
    # 处理表格
    for table in doc.tables:
        for row in table.rows:
            for cell in row.cells:
                for key, value in data.items():
                    if key in cell.text:
                        cell.text = cell.text.replace(f'[{key}]', str(value))
    
    # 保存文档
    doc.save(output_file)
    print(f"文档已生成: {output_file}")

# 使用示例
fill_word_template_from_excel('data.xlsx', 'template.docx', 'output.docx')

方法二:使用邮件合并域

1. 准备Word模板

在Word模板中使用<<字段名>>格式的合并域。

2. Python实现代码

python 复制代码
import openpyxl
from docx import Document
import re

def mail_merge_from_excel(excel_file, word_template, output_file):
    # 读取Excel数据
    wb = openpyxl.load_workbook(excel_file)
    ws = wb.active
    
    # 读取Word模板
    doc = Document(word_template)
    
    # 获取数据(假设第一行是字段名)
    headers = [cell.value for cell in ws[1]]
    data_row = ws[2]  # 假设使用第二行数据
    
    # 创建数据字典
    data = {headers[i]: data_row[i].value for i in range(len(headers))}
    
    # 替换合并域
    for paragraph in doc.paragraphs:
        for key, value in data.items():
            merge_field = f'<<{key}>>'
            if merge_field in paragraph.text:
                paragraph.text = paragraph.text.replace(merge_field, str(value))
    
    # 处理表格中的合并域
    for table in doc.tables:
        for row in table.rows:
            for cell in row.cells:
                for key, value in data.items():
                    merge_field = f'<<{key}>>'
                    if merge_field in cell.text:
                        cell.text = cell.text.replace(merge_field, str(value))
    
    # 保存文档
    doc.save(output_file)
    print(f"邮件合并完成: {output_file}")

# 使用示例
mail_merge_from_excel('employee_data.xlsx', 'offer_letter_template.docx', 'offer_letter.docx')

方法三:批量处理多条数据

python 复制代码
import openpyxl
from docx import Document
import os

def batch_generate_documents(excel_file, word_template, output_folder):
    # 创建输出文件夹
    if not os.path.exists(output_folder):
        os.makedirs(output_folder)
    
    # 读取Excel数据
    wb = openpyxl.load_workbook(excel_file)
    ws = wb.active
    
    # 获取标题行
    headers = [cell.value for cell in ws[1]]
    
    # 遍历每一行数据
    for row_idx, row in enumerate(ws.iter_rows(min_row=2), 1):
        # 读取Word模板
        doc = Document(word_template)
        
        # 创建数据字典
        data = {headers[i]: row[i].value for i in range(len(headers))}
        
        # 替换文档内容
        for paragraph in doc.paragraphs:
            for key, value in data.items():
                placeholder = f'{{{key}}}'
                if placeholder in paragraph.text:
                    paragraph.text = paragraph.text.replace(placeholder, str(value))
        
        # 处理表格
        for table in doc.tables:
            for table_row in table.rows:
                for cell in table_row.cells:
                    for key, value in data.items():
                        placeholder = f'{{{key}}}'
                        if placeholder in cell.text:
                            cell.text = cell.text.replace(placeholder, str(value))
        
        # 保存文档
        filename = f"{output_folder}/document_{row_idx}.docx"
        doc.save(filename)
    
    print(f"批量生成完成,共生成 {ws.max_row - 1} 个文档")

# 使用示例
batch_generate_documents('students.xlsx', 'certificate_template.docx', 'certificates')

方法四:使用python-docx-template(推荐)

首先安装:pip install docxtpl

python 复制代码
import openpyxl
from docxtpl import DocxTemplate
import json

def advanced_template_filling(excel_file, word_template, output_file):
    # 读取Excel数据
    wb = openpyxl.load_workbook(excel_file)
    ws = wb.active
    
    # 准备数据
    headers = [cell.value for cell in ws[1]]
    data = {}
    
    # 假设我们处理第一行数据
    for i, header in enumerate(headers):
        data[header] = ws[2][i].value
    
    # 加载Word模板
    doc = DocxTemplate(word_template)
    
    # 渲染模板
    doc.render(data)
    
    # 保存文档
    doc.save(output_file)
    print(f"高级模板填充完成: {output_file}")

# 使用示例
advanced_template_filling('contract_data.xlsx', 'contract_template.docx', 'contract_final.docx')

完整案例:生成员工录用通知书

Excel数据 (employee_data.xlsx)

姓名 职位 部门 入职日期 薪资
张三 软件工程师 技术部 2024-01-15 15000

Word模板 (offer_letter_template.docx)

复制代码
员工录用通知书

尊敬的<<姓名>>先生/女士:

我们很高兴通知您,您已被录用为<<部门>>的<<职位>>。

入职日期:<<入职日期>>
基本薪资:¥<<薪资>>元/月

请携带相关材料按时报到。

人力资源部
<<当前日期>>

Python代码

python 复制代码
import openpyxl
from docxtpl import DocxTemplate
from datetime import datetime

def generate_offer_letters():
    # 读取Excel数据
    wb = openpyxl.load_workbook('employee_data.xlsx')
    ws = wb.active
    
    # 处理每一行数据
    for row in ws.iter_rows(min_row=2, values_only=True):
        name, position, department, start_date, salary = row
        
        # 准备上下文数据
        context = {
            '姓名': name,
            '职位': position,
            '部门': department,
            '入职日期': start_date.strftime('%Y年%m月%d日') if isinstance(start_date, datetime) else start_date,
            '薪资': salary,
            '当前日期': datetime.now().strftime('%Y年%m月%d日')
        }
        
        # 加载并渲染模板
        doc = DocxTemplate('offer_letter_template.docx')
        doc.render(context)
        
        # 保存文档
        output_file = f"offer_letter_{name}.docx"
        doc.save(output_file)
        print(f"已生成: {output_file}")

# 执行
generate_offer_letters()

总结

以上方法提供了不同复杂度的Word模板填充方案:

  1. 简单替换:使用字符串替换处理简单的占位符
  2. 邮件合并:处理标准的Word合并域格式
  3. 批量处理:一次性处理多条数据记录
  4. 高级模板:使用docxtpl库处理复杂的模板逻辑

选择哪种方法取决于你的具体需求:

  • 简单需求:使用方法一或二
  • 批量处理:使用方法三
  • 复杂模板:推荐使用方法四(docxtpl)

记得安装所需库:

bash 复制代码
pip install openpyxl python-docx docxtpl
相关推荐
饼干,2 小时前
第5天python内容
开发语言·python
ZhengEnCi2 小时前
P3E-Python Lambda表达式完全指南-什么是匿名函数?为什么90%程序员都在用?怎么快速掌握函数式编程利器?
后端·python
Ace_31750887762 小时前
京东商品详情接口深度解析:从反爬绕过到数据结构化重构
数据结构·python·重构
尤利乌斯.X2 小时前
在Java中调用MATLAB函数的完整流程:从打包-jar-到服务器部署
java·服务器·python·matlab·ci/cd·jar·个人开发
听风吟丶2 小时前
Java 9 + 模块化系统实战:从 Jar 地狱到模块解耦的架构升级
开发语言·python·pycharm
love530love3 小时前
【笔记】xFormers版本与PyTorch、CUDA对应关系及正确安装方法详解
人工智能·pytorch·windows·笔记·python·深度学习·xformers
2301_764441333 小时前
Streamlit搭建内网视频通话系统
python·https·音视频
伟大的大威3 小时前
LLM + TFLite 搭建离线中文语音指令 NLU并部署到 Android 设备端
python·ai·nlu
m5655bj3 小时前
Python 查找并高亮显示指定 Excel 数据
开发语言·python·excel