You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用pdfminer.six提取PDF行序混乱,求解决方法

解决pdfminer.six提取PDF行序混乱的方案

问题重现

原PDF为一道选择题,使用pdfminer.six解析后文本顺序混乱(如选项4、5被插入到选项3与答案提示之间),输出结果如下:

Nr 48. Promująco na rozwój chorób alergicznych i wystąpienie objawów alergii 
działa zwiększenie aktywności/ilości: 

1) limfocytów Th1; 
2) limfocytów Th2; 
3) limfocytów Th17; 
Prawidłowa odpowiedź to: 
B. tylko 2. 
A. 1,4. 

4) IL-5. 
5) IL-12. 

C. 1,3. 

D. 2,4. 

E. 3,5. 

可行解决方法

1. 调整pdfminer布局分析参数

pdfminer默认布局分析对复杂排版处理不佳,可通过修改LAParams参数强制按垂直位置排序文本块:

from pdfminer.high_level import extract_text
from pdfminer.layout import LAParams

laparams = LAParams(
    line_overlap=0.5,
    char_margin=2.0,
    line_margin=0.5,
    word_margin=0.1,
    boxes_flow=0,  # 设为0表示严格按垂直位置排序,符合从上到下的阅读顺序
    detect_vertical=False
)

text = extract_text("目标PDF文件路径", laparams=laparams)
print(text)

重点关注boxes_flow:0代表优先按文本块垂直位置排序,若为分栏PDF可设为1(按水平顺序)。

2. 自定义文本排序逻辑

若默认参数仍无效,可直接获取页面布局元素,按坐标手动排序:

from pdfminer.pdfinterp import PDFResourceManager, PDFPageInterpreter
from pdfminer.converter import TextConverter
from pdfminer.layout import LAParams
from pdfminer.pdfpage import PDFPage
from io import StringIO

def extract_text_sorted(pdf_path):
    rsrcmgr = PDFResourceManager()
    retstr = StringIO()
    laparams = LAParams()
    device = TextConverter(rsrcmgr, retstr, laparams=laparams)
    fp = open(pdf_path, 'rb')
    interpreter = PDFPageInterpreter(rsrcmgr, device)
    
    sorted_text_total = ""
    for page in PDFPage.get_pages(fp):
        interpreter.process_page(page)
        # 获取当前页面的布局对象
        layout = device.cur_item
        # 按文本块顶部y坐标从高到低排序(PDF原点在左下角,y值越大位置越靠上)
        text_blocks = sorted(layout._objs, key=lambda x: (-x.y1, x.x0))
        # 拼接有效文本块
        page_text = '\n'.join([obj.get_text().strip() for obj in text_blocks if hasattr(obj, 'get_text')])
        sorted_text_total += page_text + '\n'
    
    fp.close()
    device.close()
    retstr.close()
    return sorted_text_total

# 使用示例
result = extract_text_sorted("目标PDF文件路径")
print(result)

该方法直接操作PDF布局元素,确保文本按视觉上的从上到下、从左到右顺序排列。

3. 替换工具尝试

如果pdfminer始终无法适配该排版,可切换工具:

  • PyMuPDF(fitz):对复杂排版的原生支持更好,默认排序更贴近视觉顺序:
    import fitz
    
    doc = fitz.open("目标PDF文件路径")
    full_text = ""
    for page in doc:
        full_text += page.get_text()
    print(full_text)
    

关于转HTML效果差的说明

PDF转HTML时每个单词单独被span包裹,是因为原生PDF中每个字符的位置独立存储,转译时会按字符坐标生成标签,这种情况难以直接优化,不如直接调整文本提取的排序逻辑。

内容的提问来源于stack exchange,提问作者mik.ro

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.26 03:42:42