跳转至正文内容
开发者指南

PDF 的 Tesseract OCR
与可搜索 PDF。

用 Tesseract 对 PDF 做 OCR 的完整、经过验证的指南:栅格化页面、创建可搜索 PDF、使用 OCRmyPDF 和 pdfsandwich、在 Python 中端到端运行,并解决常见错误。

摘要(一条命令)

对于真实的多页 PDF,OCRmyPDF 是最快的路径。

bash
pip install ocrmypdf      # 或:apt install ocrmypdf
ocrmypdf input.pdf output.pdf

没有 OCRmyPDF?栅格化后直接使用 Tesseract CLI —— 见下文。

为什么 PDF 必须栅格化

Tesseract 识别图片,而不是 PDF 容器。

PDF 是容器:可能包含矢量文字、嵌入字体或扫描的页面图片。Tesseract 读取栅格图片(TIFF、PNG、JPEG、WebP 等),因此必须先把页面转换为图片。根据已安装的工具选择栅格化器:

工具安装备注
pdftoppm(poppler)apt install poppler-utils快速、可脚本化,经典选择
pdftocairo(poppler)poppler-utils与 pdftoppm 类似,Cairo 输出
ImageMagickapt install imagemagickconvert -density 300 in.pdf out.tif
PyMuPDFpip install pymupdf纯 Python,无需外部二进制
pdf2imagepip install pdf2image封装 poppler 的 Python 库
bash
# PDF -> 每页一个 300 DPI 的 PNG
pdftoppm -png -r 300 input.pdf page

DPI 最重要:300 DPI 是标准平衡;小字体或归档用 600 DPI;避免低于 200 DPI。

用 Tesseract CLI 创建可搜索 PDF

使用 pdf 输出配置,一张图片就成为一页可搜索 PDF。

bash
# 图片 -> 可搜索 PDF
tesseract page-1.png output pdf

# 仅文字层(不显示图片)
tesseract scan.png output textonly_pdf

# 多页合成一个 PDF:传入图片列表
tesseract imagelist.txt output pdf

多页 PDF 时,把每个图片路径写在一行放入 imagelist.txt。完整输出格式参考:文档。

方法 B — OCRmyPDF(真实 PDF 推荐)

OCRmyPDF 用一条命令完成栅格化、OCR、纠偏、旋转和不可见文字层。

bash
ocrmypdf input.pdf output.pdf                    # 基础
ocrmypdf -l eng+chi_sim input.pdf output.pdf     # 语言
ocrmypdf --deskew --rotate-pages input.pdf output.pdf
ocrmypdf --optimize 2 input.pdf output.pdf       # 缩小文件
ocrmypdf --skip-text input.pdf output.pdf        # 保留已有文字的页面

OCRmyPDF 内部使用 Tesseract,需要 Ghostscript 和 poppler 工具。常用选项:--force-ocr、--redo-ocr、--pages 1-10。

方法 C — pdfsandwich

更轻量的封装,添加文字层并执行纠偏等预处理。

bash
pdfsandwich scan.pdf          # 生成 scan_ocr.pdf
pdfsandwich -lang eng+chi_sim scan.pdf

方法 D — Python 端到端

用 pdf2image 栅格化,用 pytesseract 构建可搜索 PDF,再用 pypdf 合并。

pdf.py
import io, pytesseract
from pdf2image import convert_from_path
from pypdf import PdfWriter, PdfReader

pages = convert_from_path("input.pdf", dpi=300)   # 需要 poppler
writer = PdfWriter()
for page in pages:
    pdf_bytes = pytesseract.image_to_pdf_or_hocr(page, extension="pdf", lang="chi_sim")
    writer.add_page(PdfReader(io.BytesIO(pdf_bytes)).pages[0])
with open("output.pdf", "wb") as f:
    writer.write(f)

在 Windows 上,通过 poppler_path= 传入 poppler 的 bin 文件夹。更多细节见 pytesseract 指南。

该用哪种方法?

方法适合配置多页
OCRmyPDF真实 PDF、自动化Ghostscript + poppler一条命令即可
pdfsandwich带预处理的快速文字层poppler + ImageMagick是
Tesseract CLI图片或图片列表仅需 Tesseract通过图片列表
Python(pdf2image)流水线与自定义逻辑poppler + pytesseract循环并合并

版面保真与文字叠加

可搜索 PDF 有时看起来错位的原因,以及如何保持几何精度。

质量与性能

故障排查

症状原因解决方法
Unable to get page count. Is poppler installed?pdf2image 找不到 poppler安装 poppler-utils,或在 Windows 上设置 poppler_path。
输出 PDF 没有可搜索文字OCR 未运行或语言错误确认成功,并把 -l/--language 设为文档语言。
文字叠加错位DPI 或页面尺寸错误以原始尺寸按 300 DPI 栅格化。
输出文件巨大600 DPI 无损图片使用 --optimize / JPEG,或降低 DPI。
受密码保护的 PDF 失败加密输入先解密,或传入工具支持的密码参数。

PDF 常见问题

如何让 PDF 可搜索?

使用 ocrmypdf input.pdf output.pdf,或栅格化页面后运行 tesseract page.tif output pdf。

为什么 Tesseract 不能直接读取 PDF?

Tesseract 识别栅格图片,因此必须先转换 PDF 页面。

该用多少 DPI?

大多数文档用 300 DPI;小字体或归档用 600 DPI。

能在 Python 中对 PDF 做 OCR 吗?

可以 —— 用 pdf2image 配合 poppler 和 pytesseract.image_to_pdf_or_hocr,再用 pypdf 合并页面。

如何保持版面精确?

保持原始页面尺寸和 DPI,并优先使用 OCRmyPDF,它保留图像并叠加文字层。