首页 > 解决方案 > python中是否有一种方法可以根据列标题提取半结构化pdf表的列?

问题描述

首先,我希望我的问题足够详细和清楚。我对 python 还比较陌生,所以如果需要,我会尽力澄清或提供更多信息。

我的目标是创建一个 pdf 阅读器,它采用半结构化的 pdf 表格并将它们加载到数据框中(最终转换为 csv 或 excel 文件)。数据具有相对一致的标题标题,但每列之间的间距在文档中不一致。

我目前正在使用 tabula 库作为主要阅读器和 pdfminer 来获取 pdf 的最后一页(并循环我的代码以提取所有数据)。请看我下面的数据:

#Library imports
import os
import pandas as pd
import tabula
import csv
from tkinter import filedialog
import tkinter as tk
from pdfminer.pdfparser import PDFParser
from pdfminer.pdfdocument import PDFDocument
from pdfminer.pdfpage import PDFPage
from pdfminer.pdfinterp import resolve1

pd.set_option("display.max_rows", 5, "display.max_columns", 7)

#Pick the pdf
root = tk.Tk() # Creates toplevel widget of tk
root.withdraw() # Gets rid of the tk root window

pdf_path_full = filedialog.askopenfilename() #Opens file dialog picker
pdf_path_only = os.path.dirname(pdf_path_full)
file_name_csv = 'Output/output.csv'

#pdf_path_full = r'C:\Users\JeffNi\OneDrive - Mirador, LLC\Documents\Python\PDfs\2021.04.15 PKS Comp Laura S.pdf'


#column area measurements
col= [83.8,115,155.7,173.4,211.5,385,410.3,435.4,479,504,522.5,554]


data = tabula.read_pdf(pdf_path_full, pages="all", columns=col, guess=False, pandas_options={'header':None})

file = open(pdf_path_full, 'rb')
parser = PDFParser(file)
document = PDFDocument(parser)

# This will give you the count of pages
last_page = resolve1(document.catalog['Pages'])['Count']


#Create dataframes to clean data and loop through the pages
df = pd.DataFrame()
df_clean = pd.DataFrame()
df_concat = pd.DataFrame()
i = 1 

#Loop to clean the data and append all pdf pages into one dataframe
for i in range(last_page):
    df = pd.DataFrame(data[i])
    df_clean = df.copy()
    df_clean.dropna(inplace = True)
    df_concat = df_concat.append(df_clean)

#Change the headers of the concat data frame
df_concat.columns = df_concat.iloc[0]

#Output dataframe as csv
df_concat = df_concat[df_concat.Source.str.contains('Source') == False]
df_concat.to_csv(file_name_csv, mode = 'w', index=False)

目前,我的代码为文档设置了确切的区域边距,但在进一步测试后我意识到这个解决方案不够好,因为 1)在同一个文档中更改边距和 2)在不同文档之间更改边距。

有没有办法让python根据某些关键短语自动检测表格区域边距?(在发布的 PDF 示例中,python 在标题行中查找文本“S/D”,确认 S 从 83.8 开始并将第一列边距设置为此,然后对“源”执行相同操作,识别 S 从 115 开始第二边距等)

抱歉,我无法包含示例 pdf,他们有我必须编辑的机密信息,而且我不是创建 pdf 的来源(或者我会直接进入源系统并尝试在那里工作)。

我觉得这是一个很长的镜头,但我感谢提供的任何输入和任何可能激发我创造力的想法。

再次感谢!

[pdf截图][1][1]:https://i.stack.imgur.com/OFQvn.png

标签: python-3.xdataframepdfscrape

解决方案


推荐阅读