Python使用pypandoc将markdown文件和LaTex公式转为word
目录
- 一 pypandoc 介绍
- 1. 项目介绍
- 2. 安装
- 二、使用python 将markdown转Word
- 三、直接指定Word格式
- 四、将LaTex公式转为Word
- 四、将LaTex公式转为Word,追加写入Word
通义千问等大模型生成的回答多数是markdown类型的,需要将他们转为Word文件
一 pypandoc 介绍
1. 项目介绍
pypandoc 是一个用于 pandoc 的轻量级 Python 包装器。pandoc 是一个通用的文档转换工具,支持多种格式的文档转换,如 Markdown、html、LaTeX、DocBook 等。pypandoc 通过提供一个简单的 Python 接口,使得在 Python 脚本中调用 pandoc 变得更加方便。
2. 安装
使用pip安装
pip install pypandoc_binary
自动下载 Pandoc并安装
注意:pypandoc 提供了两个包:
pypandoc:需要用户自行安装 pandoc软件才能使用。
pypandoc_binary:包含了预编译的 pandoc 二进制文件,方便用户快速上手。
手动安装
可以手动安装pandoc再安装pypandoc库
pip install pypandoc
也可以先安装pypandoc然后再在pyhon中运行 pypandoc.download_pandoc()函数自动下载并安装 Pandoc,将其存放在 pypandoc 可以访问的目录中。
二、使用Python 将markdown转Word
本脚本实现了三类功能
1、将markdown文件转为word文件
2、将 markdown中段落开头的“-“转为回车,避免渲染成黑点或者空心圆等Word中不常见的符号
3、自定义了模板,格式化输出。
import pypandoc import time import re # 定义路径 path1 = r"md.md" path2 = r".docx" template_path = r"D:\aTools\ytemplates\templates_s.docx" # 读取原始Markdown文件内容 with open(path1, 'r', encoding='utf-8') as file: content = file.read() # 使用正则表达式将以'- '开头的部分替换为换行符 processed_content = re.sub(r'- ', '\n', content) # 记录开始时间 t1 = time.time() # 将处理后的内容转换为编程客栈Word文档 pypandoc.convert_text( processed_content, 'docx', format='md', outputfile=path2, extra_args=['--reference-doc', template_path] ) # 打印耗时 print(time.time() - t1) print("转换完成!")
三、直接指定Word格式
直接读取文件(可以为txt或者md)转为指定格式的word。
这里格式是:
1、将 markdown中段落开头的“-“转为回车,避免渲染成黑点或者空心圆等Word中不常见的符号
2、将原来加粗部分继续加粗和左对齐
3、字体为黑色GB2312
注意:代码用正则替换####这些时需要先从4级标题开始替换否则会有逻辑错误,导致奇数个#无法替换。
设置中文字体不能用run.font.name = '仿宋_GB2312’而是用style._element.rPr.rFonts.set(qn(‘w:eastAsia’), ‘仿宋_GB2312’) 设置中文字体。
import re from docx import Document from docx.shared import Pt, RGBColor from docx.enum.text import WD_ALIGN_PARAGRAPH from docx.oXML.ns import qn def set_font_color(run): run.font.name = 'Times New Roman' run._element.rPr.rFonts.set(qn('w:eastAsia'), '仿宋_GB2312') run.font.size = Pt(12) run.font.color.rgb = RGBColor(0, 0, 0) run.italijsc = False def process_content(line, paragraph): """通用内容处理函数""" bold_pattern = re.compile(r'\*\*(.*?)\*\*') matches = list(bold_pattern.finditer(line)) if not matches: run = paragraph.add_run(line) set_font_color(run) else: start = 0 for match in matches: if match.start() > start: run = paragraph.add_run(line[start:match.start()]) set_font_color(run) run = paragraph.add_run(match.group(1)) run.bold = True set_font_color(run) start = match.end() if start < len(line): run = paragraph.add_run(line[start:]) set_font_color(run) def mdtxt2word(txt_path, docx_path): with open(txt_path, 'r', encoding='utf-8') as file: content = re.sub(r'- ', '\n', file.read()) doc = Document() style = doc.styles['Normal'] style.font.name = 'Times New Roman' style._element.rPr.rFonts.set(qn('w:eastAsia'), '仿宋_GB2312') style.font.size = Pt(12) style.font.color.rgb = RGBColor(0, 0, 0) # 合并标题正则表达式 heading_pattern = re.compile( r'^\s*(#{1,4})\s*(javascript.*?)\s*$' # 匹配1-4个#开头的标题 ) for line in content.split('\n'): # 处理所有标题类型 heading_match = heading_pattern.match(line) if heading_match: level = len(heading_match.group(1)) # 根据#数量确定级别 title_text = heading_match.group(2).strip() if not title_text: continue # 跳过空标题 # 创建对应级别的标题 heading = doc.add_heading(level=min(level, 4)) # 限制最大4级 heading.alignment = WD_ALIGN_PARAGRAPH.LEFT # 处理标题内容中的加粗标记 process_content(titwww.devze.comle_text, heading) continue # 处理普通段落 paragraph = doc.add_paragraph() paragraph.alignment = WD_ALIGN_PARAGRAPH.LEFT process_content(line, paragraph) doc.save(docx_path) print("转换完成!") if __name__ == "__main__": txt_path = r"C:\Users\xueshifeng\Desktop\11.txt" docx_path = r"C:\Users\xueshifeng\Desktop\11.docx" mdtxt2word(txt_path, docx_path)
四、将LaTex公式转为Word
将 latex_content字符串$ $ 中间的位置替换为公式,或者直接复制代码到GPT,让GPT修改代码
import pypandoc # 定义包含特定公式的LaTeX字符串 #$ $ 中间的位置替换为公式,或者直接复制代码到GPT,让GPT生成最终代码 latex_content = r""" \documentclass{article} \usepackage{amsmath} % 确保包含用于数学排版的包 \begin{document} $ L(y_i, f(x_i)) = \max(0, 1 - y_if(x_i)) $ \end{document} """ # 将LaTeX内容转换为Word文档 output_file = r"xx14.docx" output = pypandoc.convert_text( latex_content, # 输入的字符串 'docx', # 输出格式 format='latex', # 输入格式(LaTeX) outputfile=output_file, # 输出文件路径 extra_args=['--mathml'] # 额外参数,确保公式渲染为MathML格式 ) # 检查转换是否成功 if output != '': print(f"转换过程中出现错误: {output}") else: print(f"Word 文档已生成: {output_file}")
四、将LaTex公式转为Word,追加写入Word
难点在于如何管理文件句柄,没有找到好方法,采用对已打开的文档,先关闭再打开的方法。
import os import pypandoc from docx import Document import tempfile import time import pythoncom www.devze.comfrom win32com.client import Dispatch # 需要安装pywin32库 def is_file_locked(filepath): try: with open(filepath, 'a'): return False except PermissionError: return True except FileNotFoundError: return False def close_word_document(filepath): try: word = Dispatch("Word.Application") for doc in word.Documents: if doc.FullName.lower() == os.path.abspath(filepath).lower(): doc.Save() doc.Close() print("已保存并关闭Word文档") return True word.Quit() except Exception as e: print(f"关闭Word文档失败:{str(e)}") return False def generate_latex_content(formula): """生成完整的LaTeX文档内容""" return fr""" \documentclass{{article}} \usepackage{{amsmath}} \begin{{document}} 开始: ${formula}$ 结束。 \end{{document}} """ def doc_creat(user_formula, output_file): # 检查文件是否存在 if not os.path.exists(output_file): # 创建新文档对象 doc = Document() # 保存文档 doc.save(output_file) print(f"文件已创建:{output_file}") document = Document(output_file) else: print("文件已打开") retry_count = 3 for _ in range(retry_count): if is_file_locked(output_file): print("检测到文件被占用,尝试关闭Word文档...") if close_word_document(output_file): time.sleep(0.5) # 等待系统释放文件 continue else: print("错误:文件被其他程序占用,请手动关闭后重试!") break try: with tempfile.NamedTemporaryFile(delete=False, suffix=".tex") as temp_tex_file: latex_content = generate_latex_content(user_formula) temp_tex_file.write(latex_content.encode('utf-8')) temp_tex_file_name = temp_tex_file.name with tempfile.NamedTemporaryFile(delete=False, suffix=".docx") as temp_docx_file: temp_docx_file_name = temp_docx_file.name # 转换LaTeX到Word pypandoc.convert_file( temp_tex_file_name, 'docx', outputfile=temp_docx_file_name, extra_args=['--mathjax'] ) # 创建或打开目标文档 target_doc = Document(output_file) if os.path.exists(output_file) else Document() temp_doc = Document(temp_docx_file_name) # 复制所有元素 for element in temp_doc.element.body: target_doc.element.body.append(element) # 保存目标文档 target_doc.save(output_file) print(f"内容已成功追加至:{output_file}") # 自动用Word打开文档 os.startfile(output_file) break except PermissionError: print("文件权限错误,请检查文件是否被其他程序占用") break except Exception as e: print(f"操作失败:{str(e)}") break finally: if 'temp_tex_file_name' in locals() and os.path.exists(temp_tex_file_name): os.unlink(temp_tex_file_name) if 'temp_docx_file_name' in locals() and os.path.exists(temp_docx_file_name): os.unlink(temp_docx_file_name) else: print("重试次数已达上限,请检查文件状态") if __name__ == '__main__': # 用户输入公式(示例) user_formula = r"\frac{\sqrt{x^2 + y^2}}{z}" # 输出文件路径 output_file = r"C:\Users\xueshifeng\Desktop\18.docx" doc_creat(user_formula, output_file)
以上就是Python使用pypandoc将markdown文件和LaTex公式转为word的详细内容,更多关于Python pypandoc格式转换的资料请关注编程客栈(www.devze.com)其它相关文章!
精彩评论