Extrahieren Sie Bilder und Tabellen mit Python aus PDF, um die Berichtslast zu verringern

Hintergrund

Beim Schreiben eines Berichts wurde es schwierig, Bilder (Schaltpläne usw.) aus dem im PDF-Format gesendeten PDF zu schneiden und zu speichern und nur die Tabelle zu kopieren. Die nützlichen Apps und der Code, mit denen sie erstellt wurden, waren kein kurzer Überblick. Dann lass es uns schaffen. Die Tabellenextraktion hat nicht funktioniert, aber ich konnte die Werte abrufen, sodass die Belastung reduziert wurde (; ^ _ ^ A).

Ich habe es auch auf Git gesetzt, wenn es in Ordnung ist https://github.com/kzrn3318/create_img_excel_from_pdf

Umgebung

Installation der erforderlichen Bibliotheken


pip install pypdf2
pip install pillow
pip install PyMuPDF
pip install fitz
pip install pandas
pip install camelot-py[cv]

Wenn Sie zur Laufzeit kein Ghostscript haben, wird möglicherweise eine Fehlermeldung angezeigt. In diesem Fall installieren Sie bitte Ghostscript. Da es sich zum Zeitpunkt der Codeerstellung um Windows 10 handelt, funktioniert es aufgrund der Zeichenfolge des Pfads möglicherweise nicht mit anderen Betriebssystemen. In diesem Fall schreiben Sie es bitte neu, damit der Pfad des Codes angewendet werden kann. Wir haben die Operation mit anderen Betriebssystemen nicht bestätigt.

Code body

Unten ist der Code

main.py


import PyPDF2
from PIL import Image
import sys,os
import glob
import fitz
import camelot
import pandas as pd

def create_dir(img_dir , pdf_dir , excel_dir):
    img_dir_glob = glob.glob(str(img_dir))
    pdf_dir_glob = glob.glob(str(pdf_dir))
    excel_dir_glob = glob.glob(str(excel_dir))
    
    if len(pdf_dir_glob) > 0:
        pass
    else:
       os.mkdir(str(pdf_dir))
       
    if len(img_dir_glob) > 0:
        pass
    else:
        os.mkdir(str(img_dir))
    
    if len(excel_dir_glob) > 0:
        pass
    else:
        os.mkdir(str(excel_dir))
        

def create_page_pdf(pdf,page_count,pdf_dir):
    pdf_writer = PyPDF2.PdfFileWriter()
    pdf_writer.addPage(pdf.getPage(page_count))
    
    with open(".\\"+str(pdf_dir)+"\pdf{}.pdf".format(page_count),"wb") as f:
        pdf_writer.write(f)
    

def create_png(pdf_path,page_count,img_dir):
    pdf  = fitz.open(pdf_path)
    for num in range(len(pdf)):
        num_count = 0
        for image in pdf.getPageImageList(num):
            num_count += 1
            xref = image[0]
            pix = fitz.Pixmap(pdf,xref)
            
            if pix.n < 5:
                pix.writePNG(".\\"+str(img_dir)+"\img{}_{}.png ".format(page_count,num_count))
            else:
                pix = fitz.Pixmap(fitz.csRGB,xref)
                pix.writePNG(".\\"+str(img_dir)+"\img{}_{}.png ".format(page_count,num_count))
            
            pix = None
    
    pdf.close()
    
    
def create_excel(pdf_path,excel_dir,data_count):
    
    datas = camelot.read_pdf(pdf_path,split_text=True)
    data_count = data_count
    for data in datas:
        data_count += 1
        df =  data.df
        with pd.ExcelWriter(".\\"+str(excel_dir)+"\\from_pdf_{}.xlsx".format(data_count)) as file:
            df.to_excel(file,sheet_name="sheet1",index=False,header=False)
    return data_count


if __name__ == "__main__":
    args = sys.argv
    print([i for i in args])
    if len(args) >= 5:
        print("Erhielt ein Argument.")
        pdf_file = args[1]
        pdf_dir = args[2]
        img_dir = args[3]
        excel_dir = args[4]
    else:
        try:
            pdf_file = args[1]
            print("Da das Argument nicht angegeben wurde, wird der Standardwert verwendet.")
        except:
            raise ValueError("Mindestens eine PDF-Datei muss das Argument sein. Geben Sie bei der Angabe des Ausgabeverzeichnisses vier Argumente an.")
        pdf_dir ="pdf_list"
        img_dir="img_list"
        excel_dir="excel_data"
    
    pdf = PyPDF2.PdfFileReader(pdf_file)
    
    print("Bildverzeichnis:"+str(img_dir))
    print("pdf Verzeichnis jeder Seite:"+str(pdf_dir))
    print("Excel-Datenverzeichnis:"+str(excel_dir))
    
    create_dir(img_dir,pdf_dir,excel_dir)
    
    page_count = 0
    for page in pdf.pages:
        create_page_pdf(pdf,page_count,pdf_dir)
        page_count += 1
        
    path_list = glob.glob(".\\"+pdf_dir+"\*.pdf")
    page_count = 0
    data_count = 0
    for path in path_list:
        page_count += 1
        create_png(path,page_count,img_dir)
        data_count = create_excel(path,excel_dir,data_count)
        
    print("Verarbeitung beenden\n")

Die Ausführungsmethode lautet wie folgt: Bitte führen Sie sie im selben Verzeichnis wie das Ziel-PDF aus. Zum Zeitpunkt der Ausführung werden ein Verzeichnis zum Speichern der ausgelagerten PDF-Version, ein Verzeichnis zum Speichern des aus PDF extrahierten Bildes und ein Verzeichnis zum Extrahieren und Speichern der Tabelle aus PDF erstellt. Sie können sie mit Befehlszeilenargumenten angeben.

python main.py (Ziel.pdf) (pagin paginiertes Verzeichnis) (pdf Bildverzeichnis extrahieren) (Extraktionsverzeichnis für PDF-Tabellen)

Beispiel


python main.py train1.pdf pdf_dir img_dir excel_dir

Im obigen Beispiel wird PDF für jede Seitenteilung direkt unter pdf_dir gespeichert. Speichern Sie das extrahierte Bild in img_dir. Speichern Sie die extrahierte Tabelle in excel_dir, konvertiert in excel.

Teilweise Erklärung des Codes

import PyPDF2
from PIL import Image
import sys,os
import glob
import fitz
import camelot
import pandas as pd

Wie Sie sehen können, sehen es Leute, die normalerweise Python schreiben, oft. Importieren Sie jedes Paket.

def create_dir(img_dir , pdf_dir , excel_dir):
    img_dir_glob = glob.glob(str(img_dir))
    pdf_dir_glob = glob.glob(str(pdf_dir))
    excel_dir_glob = glob.glob(str(excel_dir))

    if len(pdf_dir_glob) > 0:
        pass
    else:
       os.mkdir(str(pdf_dir))

    if len(img_dir_glob) > 0:
        pass
    else:
        os.mkdir(str(img_dir))

    if len(excel_dir_glob) > 0:
        pass
    else:
        os.mkdir(str(excel_dir))

Es ist eine Verzeichniserstellungsfunktion, die bestimmt, ob das empfangene Argument bereits vorhanden ist oder nicht, und es erstellt, wenn es nicht vorhanden ist.

def create_page_pdf(pdf,page_count,pdf_dir):
    pdf_writer = PyPDF2.PdfFileWriter()
    pdf_writer.addPage(pdf.getPage(page_count))

    with open(".\\"+str(pdf_dir)+"\pdf{}.pdf".format(page_count),"wb") as f:
        pdf_writer.write(f)

Es ist eine Funktion, die das Original-PDF in Seiten unterteilt und diese speichert. Erstellen Sie pdf (Seitenzahl) .pdf direkt unter pdf_dir.

def create_png(pdf_path,page_count,img_dir):
    pdf  = fitz.open(pdf_path)
    for num in range(len(pdf)):
        num_count = 0
        for image in pdf.getPageImageList(num):
            num_count += 1
            xref = image[0]
            pix = fitz.Pixmap(pdf,xref)

            if pix.n < 5:
                pix.writePNG(".\\"+str(img_dir)+"\img{}_{}.png ".format(page_count,num_count))
            else:
                pix = fitz.Pixmap(fitz.csRGB,xref)
                pix.writePNG(".\\"+str(img_dir)+"\img{}_{}.png ".format(page_count,num_count))

            pix = None

    pdf.close()

Speichern Sie das extrahierte Bild direkt unter img_dir im PNG-Format. Der Dateiname lautet img (Seitenzahl) _ (Bildnummer auf der Seite) .png.

def create_excel(pdf_path,excel_dir,data_count):

    datas = camelot.read_pdf(pdf_path,split_text=True)
    data_count = data_count
    for data in datas:
        data_count += 1
        df =  data.df
        with pd.ExcelWriter(".\\"+str(excel_dir)+"\\from_pdf_{}.xlsx".format(data_count)) as file:
            df.to_excel(file,sheet_name="sheet1",index=False,header=False)
    return data_count

Speichern Sie das konvertierte Excel direkt unter excel_dir.

def create_excel(pdf_path,excel_dir,data_count):

    datas = camelot.read_pdf(pdf_path,split_text=True)
    data_count = data_count
    for data in datas:
        data_count += 1
        df =  data.df
        with pd.ExcelWriter(".\\"+str(excel_dir)+"\\from_pdf_{}.xlsx".format(data_count)) as file:
            df.to_excel(file,sheet_name="sheet1",index=False,header=False)
    return data_count


if __name__ == "__main__":
    args = sys.argv
    print([i for i in args])
    if len(args) >= 5:
        print("Erhielt ein Argument.")
        pdf_file = args[1]
        pdf_dir = args[2]
        img_dir = args[3]
        excel_dir = args[4]
    else:
        try:
            pdf_file = args[1]
            print("Da das Argument nicht angegeben wurde, wird der Standardwert verwendet.")
        except:
            raise ValueError("Mindestens eine PDF-Datei muss das Argument sein. Geben Sie bei der Angabe des Ausgabeverzeichnisses vier Argumente an.")
        pdf_dir ="pdf_list"
        img_dir="img_list"
        excel_dir="excel_data"

    pdf = PyPDF2.PdfFileReader(pdf_file)

    print("Bildverzeichnis:"+str(img_dir))
    print("pdf Verzeichnis jeder Seite:"+str(pdf_dir))
    print("Excel-Datenverzeichnis:"+str(excel_dir))

    create_dir(img_dir,pdf_dir,excel_dir)

    page_count = 0
    for page in pdf.pages:
        create_page_pdf(pdf,page_count,pdf_dir)
        page_count += 1

    path_list = glob.glob(".\\"+pdf_dir+"\*.pdf")
    page_count = 0
    data_count = 0
    for path in path_list:
        page_count += 1
        create_png(path,page_count,img_dir)
        data_count = create_excel(path,excel_dir,data_count)

    print("Verarbeitung beenden\n")

Dies ist der Ausführungsteil von main.py. Jeder Verzeichnisname wird aus dem Befehlszeilenargument abgerufen und ausgeführt.

Zusammenfassung

Bisher habe ich aus PDF geschnitten, aber ich denke, es ist viel einfacher geworden. pyPDF2 und camelot hatten nur sehr wenige Kratzer und waren schwierig (-_-;) Es scheint, dass es noch einige Verbesserungen bei der Tabellenextraktion gibt, aber es scheint schwierig zu extrahieren, da dies auf die Struktur und den Schreibstil von PDF zurückzuführen ist. Dieser Code wird unter der Annahme erstellt, dass das exportierte PDF verwendet wird. Bitte beachten Sie, dass wir nicht getestet haben, ob das mit Adobe Scan usw. gescannte PDF-Handbuch angewendet werden kann.

Recommended Posts

Extrahieren Sie Bilder und Tabellen mit Python aus PDF, um die Berichtslast zu verringern
Extrahieren Sie Text aus [python] pdf und lesen Sie Zeichen mit Open-Jtalk vor
Von der Einführung von JUMAN ++ bis zur morphologischen Analyse von Japanisch mit Python
Datenbanktabellen mit CSV extrahieren [ODBC-Verbindung von R und Python]
[Python] Versuchen Sie, Zeichen aus Bildern mit OpenCV und pyocr zu erkennen
Ich möchte mit Python eine beliebige URL aus der Zeichenfolge der HTML-Quelle extrahieren
Deep Learning von Grund auf neu Die Theorie und Implementierung des mit Python erlernten Deep Learning Kapitel 3
Mit matplotlib erstellte Bilder werden von dvi nach pdf verschoben
Extrahieren Sie die Tabelle der Bilddateien mit OneDrive & Python
Die Wand beim Ändern des Django-Dienstes von Python 2.7 auf Python 3-Serie
Lerne Nim mit Python (ab Anfang des Jahres).
Visualisieren Sie den Bereich der internen und externen Einfügungen mit Python
Konvertieren Sie das Bild in .zip mit Python in PDF
Ich habe versucht, das Artikel-Update des Livedoor-Blogs mit Python und Selen zu automatisieren.
Ich wollte nur die Daten des gewünschten Datums und der gewünschten Uhrzeit mit Django extrahieren
Ich habe versucht, die Verarbeitungsgeschwindigkeit mit dplyr von R und pandas von Python zu vergleichen
Ich habe versucht, die Entropie des Bildes mit Python zu finden
Extrahieren Sie die Vorlage der aus Thunderbird gespeicherten EML-Datei mit python3.7
Wahrscheinlich der einfachste Weg, um mit Python 3 ein PDF zu erstellen
Konvertieren Sie verstümmelte gescannte Bilder mit Pillow und PyPDF in PDF
Versuchen Sie, den Betrieb von Netzwerkgeräten mit Python zu automatisieren
Ich möchte die Natur von Python und Pip kennenlernen
Speichern Sie Bilder im Web mit Python (Colab) auf einem Laufwerk.
Spielen Sie mit dem Passwortmechanismus von GitHub Webhook und Python
Holen Sie sich die Quelle der Seite unbegrenzt mit Python zu laden.
Extrahieren Sie den Wert, der einem Wert am nächsten kommt, aus einem Listenelement in Python
Versuchen Sie, Merkmale von Sensordaten mit CNN zu extrahieren
So kratzen Sie mit Python den Aktienkurs einer einzelnen Aktie von der Nikkei Shimbun-Website
Geben Sie die Bilddaten mit Flask of Python zurück und zeichnen Sie sie in das Canvas-Element von HTML
Wie man die Anzahl der GPUs aus Python kennt ~ Hinweise zur Verwendung von Multiprocessing mit pytorch ~
Einführung in die KI-Erstellung mit Python! Teil 1 Ich habe versucht, die Nummer anhand des handgeschriebenen Zahlenbildes zu klassifizieren und vorherzusagen
Führen Sie Jupyter mit der REST-API aus, um Python-Code zu extrahieren und zu speichern
Extrahieren Sie die xz-Datei mit Python
Die Geschichte von Python und die Geschichte von NaN
Wiederholen Sie mit While. Skript zum Twittern oder Suchen vom Terminal aus
[Einführung in Python] Ich habe die Namenskonventionen von C # und Python verglichen.
Existenz aus Sicht von Python
Ich möchte den Anfang des nächsten Monats mit Python ausgeben
Geben Sie den Inhalt von ~ .xlsx im Ordner mit Python in HTML aus
Versuchen Sie, mit Python3 eine Zeichenfolge aus einem Bild zu extrahieren
Extrahieren Sie mit Python Text aus Bildern
Poste ein Bild von Python auf Tumblr
Verarbeiten Sie die mit Redshift entladene gzip-Datei mit Python of Lambda, gzipen Sie sie erneut und laden Sie sie in S3 hoch
Verbesserung der Wiederverwendbarkeit und Wartbarkeit von mit Luigi erstellten Workflows
Konvertieren Sie das Ergebnis von Python Optparse, um es zu diktieren und zu verwenden
Versuchen Sie, die Position des Senders aus dem Funkwellenausbreitungsmodell mit Python [Wi-Fi, Beacon] zu berechnen.
Ich habe versucht, die Effizienz der täglichen Arbeit mit Python zu verbessern
Koexistenz von Python2 und 3 mit CircleCI (1.0)
Betreiben Sie Firefox mit Selen aus Python und speichern Sie die Bildschirmaufnahme
Ich habe versucht, automatisch Bilder von Kanna Hashimoto mit Python zu sammeln! !!
Der schnellste Weg, um regelmäßig Kamerabilder mit Pythons OpenCV zu erhalten
PhytoMine-I hat versucht, mit Python die genetischen Informationen der Pflanze zu erhalten
Lösen Sie mit Python [100 ausgewählte Fragen aus der Vergangenheit, die Anfänger und Fortgeschrittene lösen sollten] (005 --- 009 Alle Suche: Alle Aufzählungen, um die Anzahl der Straßen durch Entwickeln zu reduzieren)
[Python] Drei Methoden zum Vergleichen der Liste des eindimensionalen Arrays und der Liste des zweidimensionalen Arrays und zum Extrahieren nur der übereinstimmenden Werte [json]