从PDF列明智地提取文本,其中列的大小和位置都不同

时间:2019-07-12 21:00:40

标签: pdf itext pdfbox pdftotext

我如何从PDF文件中提取文本,该文件按列划分,以使结果被该列分开?

这些列可以具有不同的高度,并且有时跨多个页面。

下面是示例PDF的图片。这就是我需要阅读文本的方式。

两条黑线之间的每个部分都是一个组。 在每个组中 第一列可以跨越多行 第二列和第三列在每一行上都相关。

我尝试了以下链接所提出的解决方案。 extract PDF text by columns但没有运气。

任何帮助将不胜感激。

enter image description here

1 个答案:

答案 0 :(得分:0)

您的问题未提及您选择的PDF库。您的标签提供了的选择。我在这里为Java选择了iText5.5.x。使用PDFBox也可以实现模拟解决方案。我不确定Pdftotext。

检查PDF的内部结构时会发现:

  • 显示说明的文本按阅读顺序排列。

    因此,您无需为提取文本而对它们进行排序,并且可以将解决方案基于SimpleTextExtractionStrategy

  • 此处或此处显示的无数单个空格字符会干扰实际文本。

    您应该过滤这些多余的空格字符。

  • 数据集分隔线是唯一填充的路径。此外,这些分隔线也按“读取顺序”绘制。

    因此,您已经可以通过填充操作识别它们,而无需分析路径形式,并且当您识别它们时,可以在文本提取策略输出中添加标记。

因此,您可以通过扩展SimpleTextExtractionStrategy来实现您的任务:

public class SimpleDividerAwareTextExtractionStrategy extends SimpleTextExtractionStrategy implements TextExtractionStrategy, ExtRenderListener {
    @Override
    public void renderText(TextRenderInfo renderInfo) {
        if (!" ".equals(renderInfo.getText()))
            super.renderText(renderInfo);
    }

    @Override
    public void modifyPath(PathConstructionRenderInfo renderInfo) { }

    @Override
    public Path renderPath(PathPaintingRenderInfo renderInfo) {
        if (renderInfo.getOperation() == PathPaintingRenderInfo.FILL)
            appendTextChunk("\n----------\n");
        return null;
    }

    @Override
    public void clipPath(int rule) { }
}

SimpleDividerAwareTextExtractionStrategy助手类)

将此策略应用于样本PDF:

PdfReader reader = new PdfReader(SOURCE);
PdfReaderContentParser parser = new PdfReaderContentParser(reader);
SimpleDividerAwareTextExtractionStrategy strategy = new SimpleDividerAwareTextExtractionStrategy();
for (int i = 1; i <= reader.getNumberOfPages(); i++)
    parser.processContent(i, strategy);
String content = strategy.getResultantText();

System.out.println(content);

DividerAwareTextExtraction测试testSimple419494453ThisIsASampleDocument

一个得到:

This is a sample document
----------

SAM PARTNERS LLC.
Existing Client with Premium
Support, Retail Client
123 Popsicle Ave
Candyville IA 50325
512-512-5555
Order Number Order Quantity
RTL123 45
RTL456 25
RTL324 95
RTL457 100
----------

DUNDER MIFFLIN
Existing Client with Standard
Support, Corporate Client
123 Lolipop Ave
Candyville PA 21325
215-512-5555
Order Number Order Quantity
RTL1234 400
RTL4565 200
----------

Mobile PARTNERS LLC.
New Client with Premium
Support, Retail Client
123 First Ave
Nashville TN 51325
514-512-5555
Order Number Order Quantity
RTL123 45
RTL456 25
RTL324 95
RTL457 25
RTL457 25
RTL457 25
RTL457 25
----------

BLUEBERRY MUFFIN
New Client, Corporate Client
123 STORM Ave
Hershey PA 50325
216-512-5555
Order Number Order Quantity
RTL1234 400
RTL4565 200
----------

要提取数据集,您只需要找到分隔符字符串----------(当然,您可以在SimpleDividerAwareTextExtractionStrategy中使用不同的字符串),然后读取直至Order Number Order Quantity的所有行。名称和地址数据,然后读取直到下一个分隔符字符串的所有行,以获取订单信息。