当前位置: 首页 > news >正文

告别报销噩梦!用Python自动化处理Uber发票,一键生成完美PDF

开篇

还记得你最后一次面对一堆Uber发票手动整理时的崩溃瞬间吗?每次出差回来,你都要把那些发票一张张摊开,像福尔摩斯一样解析日期、金额、起点和终点,还得手动输入表格。是时候改变这种繁琐的手动操作了!为什么不让Python来帮你做这些无聊的事呢?今天,我将带你实现一个能够自动解析Uber发票、生成总结页,并合并所有发票为一个整洁PDF的超级工具,从此报销不再让你抓狂!

技术工具准备

在开始之前,以下工具将成为我们的"秘密武器":

  • PyQt5:构建一个简单的图形用户界面(GUI),让工具使用起来像Windows程序一样方便,而不是依赖命令行。
  • pdfplumber:从PDF中挖掘Uber发票的详细信息,比如时间、地点、金额等。
  • PyPDF2:合并多个PDF,生成一个统一的文档。
  • reportlab:生成包含行程摘要的PDF表格。

下面是具体的代码实现。


代码实现:从文件选择到PDF合并

1. 创建主界面

首先,我们用PyQt5来创建一个简单的图形用户界面,允许用户选择包含Uber发票的文件夹,并提供一个按钮来执行PDF合并操作。下面是主界面的代码部分:

import sys
from PyQt5.QtWidgets import QApplication, QMainWindow, QFileDialog, QMessageBox
from Uber_MAINWINDOW import Ui_MainWindow  # 导入生成的UI类class MainWindow(QMainWindow):def __init__(self):super(MainWindow, self).__init__()self.ui = Ui_MainWindow()  # UI实例化self.ui.setupUi(self)  # 设置UIself.selected_folder = None# 连接按钮点击事件self.ui.pushButto_upLoadFile.clicked.connect(self.start_folder_selection)self.ui.pushButto_Merge_PDF.clicked.connect(self.merge_pdfs)# 启动文件夹选择def start_folder_selection(self):folder = QFileDialog.getExistingDirectory(self, "选择文件夹")if folder:self.selected_folder = folder  # 保存选择的文件夹路径QMessageBox.information(self, "文件夹已选择", f"已选择文件夹: {folder}")

解释:这个界面非常简洁,用户可以选择包含Uber发票的文件夹,并点击“合并PDF”按钮执行操作。我们通过PyQt5的QFileDialog让用户选择文件夹路径。

2. PDF数据提取

接下来,我们使用pdfplumber来解析Uber发票PDF,提取关键信息,如行程日期、时间、起点、终点和金额。我们定义了一个函数来处理这些发票。

import pdfplumber
import re# 提取PDF中的行程信息
def extract_trip_data_from_pdf(pdf_path):trips = []with pdfplumber.open(pdf_path) as pdf:for page in pdf.pages:text = page.extract_text()# 使用正则表达式提取日期、时间、地点和金额date_match = re.search(r'(\d{1,2}/\d{1,2}/\d{2,4})', text)time_matches = re.findall(r'(\d{1,2}:\d{2})', text)locations = re.findall(r'(\d{1,2}:\d{2}\s\|\s.+)', text)amount_match = re.search(r'Total\s([\d,.]+)\s([A-Z]{2,3})', text)if date_match and len(time_matches) >= 2 and len(locations) >= 2 and amount_match:trips.append({"日期": date_match.group(1),"起始时间": time_matches[0],"启程地": locations[0].split('|')[1].strip(),"结束时间": time_matches[1],"目的地": locations[1].split('|')[1].strip(),"金额": float(amount_match.group(1).replace(',', '')),"单位": amount_match.group(2)})return trips

解释:在这个函数中,我们利用正则表达式从PDF文本中提取出行程的日期、时间、出发地、目的地和金额。每个发票页都包含这些信息,我们将其存储在一个列表中,方便后续操作。

3. 生成总结页

接下来是生成PDF总结页的功能,它将所有行程信息汇总为一个表格,方便后续审核。

from reportlab.lib.pagesizes import A4
from reportlab.platypus import SimpleDocTemplate, Table, TableStyle
from reportlab.lib import colors# 生成总结页
def generate_summary_page(output_path, trips_data):doc = SimpleDocTemplate(output_path, pagesize=A4)table_data = [["日期", "起始时间", "启程地", "结束时间", "目的地", "金额", "单位"]]for trip in trips_data:table_data.append([trip["日期"], trip["起始时间"], trip["启程地"],trip["结束时间"], trip["目的地"], trip["金额"], trip["单位"]])table = Table(table_data)table.setStyle(TableStyle([('BACKGROUND', (0, 0), (-1, 0), colors.grey),('TEXTCOLOR', (0, 0), (-1, 0), colors.whitesmoke),('ALIGN', (0, 0), (-1, -1), 'CENTER'),('GRID', (0, 0), (-1, -1), 0.5, colors.black)]))elements = [table]doc.build(elements)

解释:这里我们使用reportlab创建一个PDF表格,总结所有提取的行程数据。该表格会成为我们合并PDF时的第一页。

4. 合并PDF文件

最后一步是将所有的发票PDF和总结页合并在一起,生成一个最终的文件。

from PyPDF2 import PdfMergerdef merge_pdfs(selected_folder, summary_pdf_path, save_path):merger = PdfMerger()merger.append(summary_pdf_path)  # 添加总结页pdf_files = [os.path.join(selected_folder, f) for f in os.listdir(selected_folder) if f.endswith('.pdf')]for pdf in pdf_files:merger.append(pdf)  # 合并所有发票merger.write(save_path)merger.close()

解释:这个函数会将生成的总结页与所选文件夹中的所有发票PDF合并,最后保存为一个新的PDF文件。


完整流程总结

从文件选择、发票解析、数据提取到最终的PDF合并,这一切都可以通过上述Python代码自动化完成!对于出差频繁的人士来说,这个工具可以极大地提高报销效率,避免手动整理发票的繁琐操作。


结语

这篇博客向你展示了如何通过Python和几个实用的库来解决日常报销中的发票整理问题。Python不仅仅是一个编程语言,它还能成为你职场生活中的高效助手!如果你也时常被Uber发票困扰,不妨动手试试吧!


http://www.mrgr.cn/news/27408.html

相关文章:

  • 【软考】归并排序
  • [通信原理]绪论2:信息量 × 信息熵
  • [Mdp] lc3290. 最高乘法得分(二维dp+状态定义+状态转移+LCS问题+好题+周赛415_2)
  • 怀孕之天赋共享:味觉新世界
  • 10年Python程序员教你多平台采集10万+电商数据【附实例】
  • Linux服务器配合Xshell+Tensorboard实现深度学习训练过程可视化
  • 字符串类型
  • 什么是机器学习力场
  • 在 Python 画图中同时设置中英文字体
  • springboot医院预约挂号系统 ---附源码73444
  • 调用智谱AI异步请求流式方法回复
  • 网络(三)——协议是什么???
  • Python-Opus——安装编解码库opus
  • 【Python刷题】Atcoder Beginner Contest 371
  • 华为OD机试 - 推荐多样性(Python/JS/C/C++ 2024 E卷 100分)
  • 指针与函数传递
  • Cisco Wireless WLC 5520 HA config and show commands
  • C++——⼆叉搜索树
  • 【吊打面试官系列-Redis面试题】使用过 Redis 分布式锁么,它是什么回事?
  • SQLite的入门级项目学习记录(三)