python提取多个pdf特定页,并合并为新pdf文件

news2024/10/6 18:34:50

文章目录

  • 1,代码结构
  • 2,代码详解
    • 2.1,将范围字符串转成list
    • 2.2,获取pdf文件特定页
    • 2.3,将pdf页list合并为pdf文件并保存
    • 2.4,遍历所有要合并的文件,进行合并
    • 2.5,给出要合并的pdf文件及范围,合并到指定文件
  • 3,完整代码
  • 4,执行结果

1,代码结构

import os
from PyPDF2 import PdfReader, PdfWriter

class PdfMerge:
    def __init__(self, fileList, dstFile):
        self.fileList = fileList
        self.dstFile = dstFile
    def readPdf(self, pdfFile, pageRange):
    def writePdf(self, pageList): 
    def getRangeList(self, rangeStr):
    def mergePdf(self):

def main():
if __name__ == "__main__":
    main()

2,代码详解

2.1,将范围字符串转成list

如:
“0:5” 转成 [0,1,2,3,4]
“0,1,2,3,6,7” 转成 [0,1,2,3,6,7]
“2” 转成 [2]

    def getRangeList(self, rangeStr):
        rangeList = []
        if rangeStr.find(':') >= 0:
            r = rangeStr.split(':')
            if len(r) != 2:
                print("rangeStr[%s] split [:] failed!"%(rangeStr))
                return rangeList
            mi = int(r[0])
            ma = int(r[1])
            for i in range(mi, ma):
                rangeList.append(i)
        elif rangeStr.find(',') >= 0:
            r = rangeStr.split(',')
            mi = int(r[0])
            ma = int(r[1])
            for i in r:
                rangeList.append(int(i))
        elif rangeStr.isnumeric():
            rangeList.append(int(rangeStr))
        else:
            print("rangeStr split failed! not find [:] and [,]")
        return rangeList

2.2,获取pdf文件特定页

    def readPdf(self, pdfFile, pageRange):
        pageList = []
        pdf_reader = PdfReader(pdfFile)
        for i in range(len(pdf_reader.pages)):
            if i in pageRange:
                pageList.append(pdf_reader.pages[i])
        return pageList

2.3,将pdf页list合并为pdf文件并保存

    def writePdf(self, pageList): 
        pdf_writer = PdfWriter()
        for page in pageList:
            pdf_writer.add_page(page)
        with open(self.dstFile, 'wb') as out:
            pdf_writer.write(out)

2.4,遍历所有要合并的文件,进行合并

    def mergePdf(self):
        pageList = []
        for pdf in self.fileList:
            file = pdf["file"]
            fileRange = self.getRangeList(pdf["range"])
            print("file[{}] rangeStr[{}] rangeList{}".format(file, pdf["range"], fileRange))
            pageList.extend(self.readPdf(file, fileRange))
        self.writePdf(pageList)

2.5,给出要合并的pdf文件及范围,合并到指定文件

def main():
    fileList = [{"file":"source/1_任务书.pdf", "range":"0:10"},{"file":"source/20230409074902162.pdf", "range":"0"}]
    #fileList = [{"file":"source/1_任务书.pdf", "range":"0,1,5,6,7"},{"file":"source/20230409074902162.pdf", "range":"0"}]
    fileProcess = PdfMerge(fileList, "source/任务书.pdf")
    fileProcess.mergePdf()

3,完整代码

import os
from PyPDF2 import PdfReader, PdfWriter

class PdfMerge:
    def __init__(self, fileList, dstFile):
        self.fileList = fileList
        self.dstFile = dstFile
       
    def readPdf(self, pdfFile, pageRange):
        pageList = []
        pdf_reader = PdfReader(pdfFile)
        for i in range(len(pdf_reader.pages)):
            if i in pageRange:
                pageList.append(pdf_reader.pages[i])
        return pageList
    
    def writePdf(self, pageList): 
        pdf_writer = PdfWriter()
        for page in pageList:
            pdf_writer.add_page(page)
        with open(self.dstFile, 'wb') as out:
            pdf_writer.write(out)
    
    def getRangeList(self, rangeStr):
        rangeList = []
        if rangeStr.find(':') >= 0:
            r = rangeStr.split(':')
            if len(r) != 2:
                print("rangeStr[%s] split [:] failed!"%(rangeStr))
                return rangeList
            mi = int(r[0])
            ma = int(r[1])
            for i in range(mi, ma):
                rangeList.append(i)
        elif rangeStr.find(',') >= 0:
            r = rangeStr.split(',')
            mi = int(r[0])
            ma = int(r[1])
            for i in r:
                rangeList.append(int(i))
        elif rangeStr.isnumeric():
            rangeList.append(int(rangeStr))
        else:
            print("rangeStr split failed! not find [:] and [,]")
        return rangeList
 
    def mergePdf(self):
        pageList = []
        for pdf in self.fileList:
            file = pdf["file"]
            fileRange = self.getRangeList(pdf["range"])
            print("file[{}] rangeStr[{}] rangeList{}".format(file, pdf["range"], fileRange))
            pageList.extend(self.readPdf(file, fileRange))
        self.writePdf(pageList)

def main():
    fileList = [{"file":"source/1_任务书.pdf", "range":"0:10"},{"file":"source/20230409074902162.pdf", "range":"0"}]
   # fileList = [{"file":"source/1_任务书.pdf", "range":"0,1,5,6,7"},{"file":"source/20230409074902162.pdf", "range":"0"}]
    fileProcess = PdfMerge(fileList, "source/任务书.pdf")
    fileProcess.mergePdf()

if __name__ == "__main__":
    main()

4,执行结果

在这里插入图片描述
在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/416223.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

大模型学习

大模型学习计算机视觉方向ViTImage Token EmbeddingMulti-head Self-attentionStable Diffusionstable diffusion支持功能stable diffusion整体结构ClipText如何训练图像信息创建器(Image information creator)自动编码解码器(降噪绘制图形&a…

One Note插件——gem for onenote的安装

文章目录一、前言二、报错原因三、解决方法一、前言 平时写笔记都是用的OneNote来记录,但是Onenote没有 Markdown编辑器 ,写起来很不方便,搜索了解后知道gem for OneNote这个插件,于是下载安装了,但是插件每次都要手动勾选&#…

什么是小程序SDK?安全吗?

前面分享了很多小程序相关的内容,常常提到小程序SDK的概念,但似乎有很多小伙伴不是很理解,今天就来跟大家聊聊小程序SDK。 什么是小程序SDK? 小程序SDK是一种开发工具包,用于开发和构建小程序应用程序。它提供了一系列…

【thingsboard+chirpstack 下行数据通信测试】

这里写目录标题 7. 节点未收到 tb 平台下发数据原因分析7.1 收到的size为07.2 节点收不到数据7.3 可以收到数据的一组例子7.4 节点没收到数据原因分析本文主要描述 tb 下发的数据,节点接收不到原因分析。 主要是数据格式以及解析脚本的对应关系 7. 节点未收到 tb 平台下发数据…

Golang数据类型比较

直接使用比较的情况 分类说明是否能比较说明基本类型整型( int/uint/int8/uint8/int16/uint16/int32/uint32/int64/uint64/byte/rune等)浮点数( float32/float64)复数类型( complex64/complex128)字符串&a…

《Vue3实战》 第一章 nods/npm安装、配置

1、nods.js安装(Windows) 1.1、下载并安装node https://nodejs.org/en/ , 安装到d盘nodejs目录 1.2、配置环境变量 path配置 1.3、配置全局包存放目录和缓存目录 在根目录下创建node_global(全局包存放目录)和node_cache&…

关于药物|新药|药品市场调研报告(实操资料分享)

药品市场调研报告是指对药品行业进行详细的市场情况研究和分析。往往伴随着药品市场调研目的地不同,如战略探索、新药开发、投资决策等,报告编辑的内容要点要求也不一样。但总的核心要点内容笔者已提炼,如下: 一、药品市场调研报告…

DeePMD-kit 配置环境备忘

版本 Conda Conda是一个开源的包管理系统和环境管理系统,用于安装多个版本的软件包及其依赖项,并在它们之间轻松切换。它可以在Linux、OS X和Windows上运行,是为Python程序创建的,但可以打包和分发任何软件。 conda enactivatec…

为何ChatGPT如此擅长编造故事?

“幻觉”——人工智能中的一个偏见性术语 AI聊天机器人(如OpenAI的ChatGPT)依赖于一种称为“大型语言模型”(LLM)的人工智能来生成它们的响应。LLM是一种计算机程序,经过数百万文本源的训练,可以阅读并生成“自然语言”文本语言,就像人类自然…

TCP报头结构和TCP协议特性

TCP报头结构 原端口号/目的端口号:表示数据是从哪个进程来,到哪个进程去; 32位序号/32位确认号:这个序号是取的发送方发送所用数据下一个字节的序号,发送方的序列号和接收方的确认号一样,才算接收成功&…

敏捷开发模式下如何用 PingCode 这类工具进行版本发布管理

在软件团队工作中,版本发布要达到好的发布效果,需要在版本发布前做好版本发布的规划,并对发布流程和进度进行管理 准备工作: 您已经创建了一个 PingCode 帐户【快速注册入口】 您创建了一个 PingCode Scrum或 Kanban 项目 您的…

【周末闲谈】文心一言,模仿还是超越?

个人主页:【😊个人主页】 系列专栏:【❤️周末闲谈】 周末闲谈 ✨第一周 二进制VS三进制 文章目录周末闲谈前言一、背景环境二、文心一言?(_)?三、文心一言的优势?😗😗😗四、文心一…

使用 arm 架构实例搭建 Harbor

使用 arm 架构实例搭建 Harbor事情准备(使用甲骨文云上实例时的准备事项)第1步,准备自签名证书第2步,安装Docker-ce第3步,构建arm镜像第4步,安装Harbor第5步,访问Harbor第6步,上传镜…

TensorFlow 深度学习第二版:1~5

原文:Deep Learning with TensorFlow Second Edition 协议:CC BY-NC-SA 4.0 译者:飞龙 本文来自【ApacheCN 深度学习 译文集】,采用译后编辑(MTPE)流程来尽可能提升效率。 不要担心自己的形象,只…

2023年【第十四届蓝桥杯】省赛java b组填空题

第一题 令 S 1! 2! 3! ... 202320232023!,求 S 的末尾 9 位数字。 提示:答案首位不为 0。 考试时的想法以及题解: 如果我们直接按照题目描述直接来求每个阶乘和的话恐怕没有什么数据类型能够胜任,在考试时我一开始使用了…

Linux中的read/write和recv/send的区别,并使用recv/send实现简单的聊天功能

Linux中的read/write和recv/send的区别read/writeread/writeread/write的用法recv/sendrecv/sendrecv/send的用法LinuxLinuxLinux中的read/writeread/writeread/write和recv/sendrecv/sendrecv/send的区别下面是一个使用read/write进行文件读写操作的例子:下面是一个…

【云原生】Kubernetes(k8s)部署 MySQL+Dubbo+Nacos服务

一、说明二、部署 MySQL三、部署 Nacos四、部署 Dubbo 服务4.1. 创建镜像仓库的密钥4.2. 部署 provider 服务4.3. 部署 consumer 服务五、测试一、说明 本文介绍基于 Kubernetes(k8s) 环境集成阿里云 私有镜像仓库 来部署一套 Dubbo Nacos 的微服务系统,并使用 Ku…

VUE前端项目环境搭建

背景: 想要使用vue搭建一个前端项目,写个小网站练练手,因为没有前端经验,所以从网上找了一个vue得开源模板使用,经过一番挑选选中了字节公司花裤衩大佬开源得项目,地址如下: 开源项目地址&…

第三代api自动化测试框架使用教程(pytest+allure+sql+yaml)

使用教程一、配置1、环境配置2、框架配置3、启动入口二、用例编写1、用例模板2、参数依赖写法2、函数(方法插件)写法3、接口上传文件和表单参数4、接口上传json参数5、接口无数据填写6、code断言7、body断言7、json断言8、sql断言9、完整断言写法&#x…

三种不同实现ublk的零拷贝I/O的方法

用户态块设备ublk,就是提供/dev/ublkbX这样的标准块设备给业务,业务读写这个块的实际IO处理由编写的用户态的代码决定。这就好比使用FUSE,所有对挂载于FUSE的目录的读写都是编写的IO handler来处理一样。使用用户态块设备,可以方便…