Python調(diào)用paddleocr編寫一個桌面端PDF識別工具
一. 前言
近期在研究 OCR 的一些工具 ,想著先試試本地識別 , 后面再嘗試一下 AI 的效率,最后選出一個好點(diǎn)的 。
這一篇主要是了解了一下 paddleocr 的使用。
二. 安裝啟動
官方使用文檔 :github.com/PaddlePaddle/PaddleOCR/blob/main/README_cn.md
環(huán)境準(zhǔn)備
我這里使用的是 Anaconda 建的虛擬環(huán)境 ,以下可以跳過
conda create --prefix "D:\code\python\enviroment\pdf_env" python=3.11.9
conda activate "D:\code\python\enviroment\pdf_env"
Anaconda
# 安裝基礎(chǔ)組件 pip install PyQt6 pip install PyQt6-WebEngine pip install PyQt6-Frameless-Window pip install PyQt6-Fluent-Widgets -i https://pypi.org/simple/ # 安裝 paddleocr pip install paddleocr # 安裝 paddlepaddle (這里為了避免性能要求高,所以采用CPU 版本) # 另外還有性能更好的 GPU 版本 -> https://www.paddlepaddle.org.cn/install/quick python -m pip install paddlepaddle==3.1.0 -i https://www.paddlepaddle.org.cn/packages/stable/cpu/ # 安裝 PyMuPDF 用于處理 PDF pip install PyMuPDF
運(yùn)行項目 (CPU )
結(jié)果是出來了 ,但是這性能太嚇人了 ,我這 CPU 也不算差呀
換個 GPU 試試
python -m pip uninstall paddlepaddle
查看自己的版本(Windows 版本)
nvidia-smi
安裝對應(yīng)版本
python -m pip install paddlepaddle-gpu==3.1.0 -i https://www.paddlepaddle.org.cn/packages/stable/cu126/
三. 核心代碼
import os import fitz # PyMuPDF from paddleocr import PaddleOCR import time from datetime import datetime from prettytable import PrettyTable import csv import traceback import logging import json # 配置日志 logging.basicConfig( level=logging.INFO, format='%(asctime)s - %(name)s - %(levelname)s - %(message)s', handlers=[ logging.FileHandler("ocr_service.log"), logging.StreamHandler() ] ) logger = logging.getLogger("OCR_Service") def ocr_pdf_pages(pdf_path: str, page_numbers: list[int], output_dir: str = None): """ 使用 PaddleOCR 對 PDF 文件的指定頁面進(jìn)行 OCR,并將結(jié)構(gòu)化結(jié)果統(tǒng)一導(dǎo)出到 CSV。 Args: pdf_path (str): PDF 文件的路徑。 page_numbers (list[int]): 需要讀取的頁碼列表 (例如 [1, 3, 5])。 output_dir (str, optional): 輸出結(jié)果的目錄。如果指定,將保存圖片、JSON 和匯總的 CSV 文件。 """ start_time = time.time() start_datetime = datetime.now().strftime("%Y-%m-%d %H:%M:%S") logger.info(f"開始處理時間: {start_datetime}") if not os.path.exists(pdf_path): logger.error(f"錯誤:找不到 PDF 文件 '{pdf_path}'") return # 初始化 PaddleOCR 引擎 logger.info("正在初始化 PaddleOCR 引擎,這可能需要一些時間...") ocr_start_time = time.time() ocr = PaddleOCR( # --- 核心功能與模型設(shè)置 --- lang="ch", # 1. 語言:指定為中文模型('ch' 支持中英文和數(shù)字) ocr_version="PP-OCRv5", # 2. 模型版本:使用先進(jìn)的PP-OCRv5 use_angle_cls=False, # 3. 方向矯正:自動檢測文字方向并旋轉(zhuǎn)圖片 # device="gpu:0", # (新版推薦) 這是更現(xiàn)代的寫法,指定使用0號GPU use_tensorrt=False, # 5. TensorRT加速:在NVIDIA GPU上獲得極致性能 (需提前安裝TensorRT) precision='fp16', # 6. 精度:使用半精度(fp16),速度更快,顯存占用更低 (需要GPU支持) # --- 性能與設(shè)備優(yōu)化 (CPU用戶) --- enable_mkldnn=True, # 7. MKLDNN加速:若在CPU上運(yùn)行,此選項可提升Intel CPU的性能 cpu_threads=6, # 8. CPU線程數(shù):在CPU模式下運(yùn)行時使用的核心數(shù) # --- 效果微調(diào) --- text_rec_score_thresh=0.5, # 9. 識別閾值:只返回置信度高于 0.5 的識別結(jié)果,過濾掉模糊的猜測 ) ocr_end_time = time.time() logger.info(f"引擎初始化完成。耗時: {ocr_end_time - ocr_start_time:.2f} 秒") # 如果指定了輸出目錄,確保它存在 if output_dir: os.makedirs(output_dir, exist_ok=True) # 初始化列表以保存所有頁面的數(shù)據(jù),用于最后統(tǒng)一導(dǎo)出 all_csv_rows = [] csv_header = ['page', 'text', 'score', 'x_min', 'y_min', 'x_max', 'y_max'] try: # 打開 PDF 文件 doc = fitz.open(pdf_path) # 遍歷指定的頁碼 for page_num in page_numbers: page_start_time = time.time() # 驗證頁碼是否在有效范圍內(nèi) (fitz 從 0 開始索引, 用戶輸入從 1 開始) if not (1 <= page_num <= doc.page_count): logger.warning(f"警告:頁碼 {page_num} 超出范圍 (總頁數(shù): {doc.page_count})。已跳過。") continue logger.info(f"\n--- 正在處理第 {page_num} 頁 ---") # 加載頁面并轉(zhuǎn)換為高分辨率圖像 page = doc.load_page(page_num - 1) pix = page.get_pixmap(dpi=300) temp_img_path = f"temp_page_{page_num}.png" pix.save(temp_img_path) # 進(jìn)行 OCR 識別 predict_start_time = time.time() result = ocr.predict(input=temp_img_path) predict_end_time = time.time() logger.info(f"OCR 識別耗時: {predict_end_time - predict_start_time:.2f} 秒") # 處理單頁的識別結(jié)果 # predict 返回一個列表,對于單個圖像,我們只關(guān)心第一個元素 page_result_obj = result[0] if result else None if page_result_obj: # 你原來的代碼 page_result_obj.print() page_result_obj.save_to_img("output") page_result_obj.save_to_json("output") # --- 新增代碼 --- # 1. 使用點(diǎn)號(.)直接獲取 rec_texts 屬性的值,并存入新變量 all_texts all_texts = page_result_obj['rec_texts'] # 2. (可選) 打印這個新變量,驗證結(jié)果 print("成功提取的文本內(nèi)容:", all_texts) # 現(xiàn)在 all_texts 就是一個列表,包含了所有識別出的文本 # 你可以對它進(jìn)行任何操作,比如遍歷 for text_item in all_texts: print(f"識別到的單項文本: {text_item}") else: logger.info(f"--- 第 {page_num} 頁未識別到文本 ---") # 刪除臨時圖像文件 if os.path.exists(temp_img_path): os.remove(temp_img_path) page_end_time = time.time() logger.info(f"第 {page_num} 頁處理完成,耗時: {page_end_time - page_start_time:.2f} 秒") doc.close() except Exception as e: # 使用 traceback.format_exc() 獲取完整的異常棧字符串 error_stack = traceback.format_exc() # 將其與您的自定義信息一起打印出來 logger.error(f"處理 PDF 時發(fā)生嚴(yán)重錯誤:\n{error_stack}") # 在所有頁面處理完畢后,將收集到的數(shù)據(jù)寫入一個 CSV 文件 if output_dir and all_csv_rows: csv_path = os.path.join(output_dir, "structured_ocr_results.csv") logger.info(f"\n正在將所有結(jié)果匯總到: {csv_path}") try: with open(csv_path, 'w', newline='', encoding='utf-8-sig') as f: writer = csv.writer(f) writer.writerow(csv_header) writer.writerows(all_csv_rows) logger.info(f"? 匯總 CSV 文件已成功保存!") except IOError as e: logger.error(f"? 匯總導(dǎo)出 CSV 文件失敗: {e}") end_time = time.time() end_datetime = datetime.now().strftime("%Y-%m-%d %H:%M:%S") total_time = end_time - start_time logger.info(f"\n處理結(jié)束時間: {end_datetime}") logger.info(f"總處理時間: {total_time:.2f} 秒 ({total_time/60:.2f} 分鐘)")
使用效果 :
四. 使用時的一些注意事項
PaddleOCR 對象的準(zhǔn)備
關(guān)于請求參數(shù)的作用
def predict( self, # 待識別的圖片,可以是路徑、URL或圖片數(shù)據(jù) input, # 是否自動旋轉(zhuǎn)圖片方向 use_doc_orientation_classify=None, # 是否自動校正彎曲圖片 use_doc_unwarping=None, # 是否自動判斷文本行方向 use_textline_orientation=None, # 臨時修改文本檢測模型的最長邊限制 text_det_limit_side_len=None, # 臨時修改文本檢測的最長邊限制類型 text_det_limit_type=None, # 臨時修改文本檢測的二值化閾值 text_det_thresh=None, # 臨時修改文本檢測的檢測框得分閾值 text_det_box_thresh=None, # 臨時修改文本檢測的文本框擴(kuò)大比例 text_det_unclip_ratio=None, # 臨時修改文本識別的置信度閾值 text_rec_score_thresh=None, # 結(jié)果保存格式 (txt, json, pdf, pdf_searchable) save_format=None, # 結(jié)果保存路徑 save_path=None, # 結(jié)果可視化或生成PDF時使用的字體路徑 font_path=None, ): # ... 函數(shù)的具體實現(xiàn)邏輯 ... pass
Result 結(jié)果
源碼 @ gitee.com/antblack/ant-tools/tree/Tools-PDF
以上就是Python調(diào)用paddleocr編寫一個桌面端PDF識別工具的詳細(xì)內(nèi)容,更多關(guān)于Python paddleocr識別PDF的資料請關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
Python實現(xiàn)按目錄層級輸出文件名并保存為excel
當(dāng)我們發(fā)現(xiàn)電腦的內(nèi)存很滿,或平時工作中文件夾管理不清晰,導(dǎo)致里面的文件數(shù)據(jù)很雜亂,查找很不方便,一個一個文件夾去看去找然后刪除又很浪費(fèi)時間。本文將介紹如何利用Python實現(xiàn)按目錄層級輸出文件名并保存為excel,需要的可以參考一下2022-02-02python3.8動態(tài)人臉識別的實現(xiàn)示例
這篇文章主要介紹了python3.8動態(tài)人臉識別的實現(xiàn)示例,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2020-09-09在IIS服務(wù)器上以CGI方式運(yùn)行Python腳本的教程
這篇文章主要介紹了在IIS服務(wù)器上以CGI方式運(yùn)行Python腳本的教程,雖然IIS的性能并不理想...需要的朋友可以參考下2015-04-04