ARTICLE DETAIL

资讯详情

深耕网站视觉设计与运营推广的一线实战洞察。

PDF 进 RAG 知识库,图表和截图到底该怎么抽?

PDF 进 RAG 知识库,图表和截图到底该怎么抽? 做 PDF 知识库时我们碰到过一个很典型的问题。用户问「这份报告里有没有市场份额相关的图」文字已经检索到了正确页面但系统返回的“相关图片”却可能是页眉 Logo甚至只是一条装饰性的分割线。原因很直接。如果只是遍历 PDF 里的 image object把所有能抽出来的图片都入库程序并不知道哪张是数据图表哪张是架构图哪张只是 Logo。一份研报或技术文档里真正有信息量的图可能只有十几张但 PDF 文件内部能扫出来的图片资源往往远不止这些。所以我们在做企业级 AI 知识库「有谷大脑」时PDF 抽图真正解决的不是怎么把 PDF 里的图片全部导出来而是怎么找到真正有信息量的图并且保留它和原文之间的关系这件事比想象中麻烦因为 PDF 里的“图”本身就不是一种东西。一、PDF 里的“图”其实至少有三种先看最基础的问题PDF 里的一张图到底是怎么存进去的常见情况大致分三类。Embedded Bitmap内嵌位图PDF 文件里真的保存了一张 JPEG、PNG 或其他压缩格式的位图资源通常有独立的 xref。这类最好处理可以直接从 PDF 中提取原始图片数据不需要先把整页渲染成截图。Vector Drawing向量绘图有些折线图、流程图、架构图看起来明明是一张完整的图但 PDF 内部保存的可能只是一组moveto lineto stroke fill ...这样的绘图指令。它没有一张完整的 JPEG 或 PNG 可以直接抽出来。如果只遍历get_images()这类图可能完全找不到。扫描版 PDF扫描件通常是一整页 bitmap。文字、表格、图片、印章全都混在这一张大图里。Native 路径虽然可能找到 image但看到的是整页。它并不知道页面中间还有一张数据图右下角还有一个示意图。所以只靠 PDF 文件结构解析覆盖不了所有情况。这也是有谷大脑的 PDF 图片解析为什么同时使用Native 结构解析 VL Layout 检测。二、第一路从 PDF 文件结构里找 Native Candidate对于 Embedded Bitmap最直接的方法还是读取 PDF 自己的结构。这一层主要回答两个问题PDF 里有哪些原生图片资源它们出现在页面的什么位置例如用 PyMuPDFforpage_indexinrange(len(doc)):pagedoc[page_index]pw,phpage.rect.width,page.rect.height seen_xrefs:set[int]set()forimginpage.get_images(fullTrue):xrefimg[0]ifxrefinseen_xrefs:continueseen_xrefs.add(xref)forrectinpage.get_image_rects(xref):bbox_norm(rect.x0/pw,rect.y0/ph,rect.x1/pw,rect.y1/ph,)candidates.append({page:page_index,xref:xref,bbox:bbox_norm,source:native,})这里有几个工程细节比较重要。seen_xrefs做的是页内去重。因为它是在每一页重新创建的所以只能避免同一页里的同一个 xref 被重复处理。如果一个 Logo 在 50 页里重复出现跨页重复不能靠这里解决后面还需要在 asset 层做内容去重。bbox 尽早归一化。PyMuPDF 返回的是 PDF 页面坐标而视觉模型可能返回像素坐标或者[0,1]范围内的归一化坐标。为了后续稳定做 IoU 匹配有谷会在 Native Candidate 阶段先把 bbox 统一到[0,1]。极小图片先做过滤或降权。PDF 里经常存在大量小图标、装饰点、透明像素、页面组件。在当前的一些文档处理中我们会根据图片 bbox 占页面面积的比例做初筛例如对面积占比非常低的候选提前过滤或降权减少后续计算。但这里的面积阈值只是工程参数。不能简单理解成小图一定没有信息。某些技术手册里的局部示意图、小型状态图本身也可能有价值。做到这里我们只知道PDF 结构里哪些位置存在图片资源。但还不知道它到底是一张数据图还是 Logo。三、第二路VL Layout 判断“这一块到底是什么”有谷会把 PDF 页面渲染成图片再交给视觉 Layout 模型做区域识别。这一路和 Native 做的事情不一样。Native 关心PDF 文件内部有没有 image objectVL Layout 关心从页面视觉和语义上看这一块到底是什么比如一页可能被识别成title text table figure header footer每个区域都有对应的 bbox 和 confidence。图片提取最关心的是figure也就是数据图、架构图、流程图、产品截图等真正具有视觉语义的区域。这一步刚好可以补 Native 的盲区。比如一张纯向量绘制的折线图。PDF 内部可能根本不存在完整的 image object但 VL Layout 可以看出来这里是一张 figure。扫描 PDF 也是一样。Native 看到的是整页图片而 VL 可以继续把页面拆成正文 表格 图片 页眉 页脚在实际处理中Layout confidence 会设置一个过滤阈值。具体数值会根据模型、文档类型和测试结果调整而不是固定套一个值。四、有谷大脑怎么把 Native 和 VL 两路结果合起来到这里我们已经有两组结果。Native Candidate告诉我们PDF 文件结构里这里存在图片资源。VL Candidate告诉我们从视觉语义上看这里是一个 figure。有谷会先把两路 bbox 统一到同一个坐标系再通过 IoU 做空间匹配。IoU也就是 Intersection over Union交并比表示两个 bbox 的重叠程度IoU 两个 bbox 的交集面积 / 两个 bbox 的并集面积在当前实现中IoU 阈值属于可调参数会根据 Layout 模型和测试集做校准。匹配以后大致有三种情况。Native VL 都命中PDF 结构里有原始图片VL 也认为这里是 figure。这是最理想的情况。既然 PDF 已经提供了原图就优先从 Native 路径直接提取原始像素不再从页面截图里二次裁剪。能拿原图就不重新截图。Native OnlyPDF 结构里有 image object但 VL 没有把它判断成 figure。这一类经常是Logo页眉图标装饰图背景纹理小型 UI 元素从 PDF 文件结构看它们当然是图片。但从知识库角度看通常没有太高的检索价值。所以这类 Native Only Candidate 一般不会直接作为有效图片资产入库。Layout OnlyVL 明确检测到了 figure但 Native 没找到匹配的原生图片资源。典型情况就是向量绘图扫描页面里的局部图表这时候没有原始 image object 可以提取就走页面渲染 → 根据 VL bbox 裁剪 → 保存图片资产所以这里有一个需要说清楚的地方并不是“只有 Native 和 VL 两路都认可的图片才保留”。更准确的逻辑是VL 负责判断这个视觉区域有没有语义价值Native 负责在有原始资源时尽可能提供原图。有 Native 原图优先拿原图。没有 Native但 VL 明确发现了有意义的图就从页面渲染结果里裁出来。只有 Native、VL 没有识别为有效 figure 的内容则通常过滤掉。五、为什么不能只用 PyMuPDF也不能只用视觉模型放在一起看会比较直观。方案优点主要问题只用 PDF Native快能直接拿原始图片不理解图片语义Logo 和图表都会被找到纯向量 figure 可能拿不到完整原图只用 VL Layout能判断 figure、table、header 等区域通常拿到的是 bbox原图定位和高清资源提取还要另外处理Native VL同时利用 PDF 结构和视觉语义实现更复杂需要统一坐标、候选匹配和回退逻辑简单说Native 更擅长回答文件里有什么VL 更擅长回答页面上的这个东西是什么对于 PDF 知识库两边的信息都需要。六、图片抽出来以后还要和 Text Chunk 对上图片单独存下来其实只完成了一半。如果最终只是image_001.png image_002.png image_003.png对 RAG 的帮助并不大。更重要的是知道这张图来自哪一页附近是什么文字对应哪个 Text Chunk用户检索到正文时能不能把相关图片一起带回来所以在有谷大脑里图片不会作为完全孤立的 asset 保存。解析阶段会保留类似这样的关系document ↓ page ├── text chunk ├── text chunk └── image assetNative 图片可以保留page_index xref bboxLayout Only 的图片则记录page_index bbox asset_path裁剪后的图片会保存到对象存储中供后续检索和前端展示使用。这样用户问这份报告里市场份额最高的是哪家公司文本检索先找到市场份额分析所在的 chunk系统再通过页面和空间关系找到对应的饼图。最终返回的不只是一个文字答案还可以把原始图表一起带回来。这也是图片进入知识库后真正有价值的地方图不是单独存着而是能重新回到它所在的文档上下文。七、扫描版 PDF 为什么要单独处理扫描 PDF 有一个很明显的特征Native 路径可能真的找到一张 image但这张 image 几乎覆盖整页。比如┌───────────────────────┐ │ │ │ 整页扫描图片 │ │ │ │ 文字 表格 图表 │ │ │ └───────────────────────┘这时候不能直接把整页当成一张“有效图片”入库。在有谷当前的处理中会根据 Native Candidate 对页面的覆盖比例做判断。例如在部分测试中我们会把覆盖页面绝大部分区域的 candidate 视为“扫描页整体”不走普通 Embedded Image 路径而是继续让整页走 VL Layout。然后再从页面中找扫描页 ↓ VL Layout ├── text ├── table └── figure真正的 figure 再按 bbox 裁出来。原稿里提到的85%可以作为当前测试中的经验参数理解而不是所有 PDF 都应该固定使用的标准值。混合型 PDF 也可以逐页判断。例如前 10 页是正常排版 PDF第 11 页是扫描附件两套处理方式可以在同一个文件里同时存在。八、同一张图出现几十次怎么去重PDF 里另一个很实际的问题是重复图片。比如公司 Logo 每页出现一次同一张产品渲染图在多个章节重复使用。前面的seen_xrefs只能解决页内重复。真正跨页甚至跨 xref 的去重会放到图片 asset 层处理。有谷目前会对提取后的图片内容计算哈希例如 MD5Page 1 ─┐ Page 8 ─┼──→ image_asset_001 Page 15 ┘相同内容的图片只保存一份 asset。但每个 page 与这张图片之间的引用关系仍然保留。也就是说图片资产可以去重图片出处不能丢。如果后续需要解决“视觉内容一样但图片编码不同”的情况还可以继续增加感知哈希或者视觉向量级近似去重。九、实际跑一份研报会发生什么以我们测试过的一类约 30 页行业研报为例。通过 PyMuPDF 扫描 PDF 内部资源时可以找到大约85120 个 Embedded Image Candidate。这里面包含不少每页重复出现的 Logo页眉、页脚装饰元素分割线小图标真正的数据图表真正有信息量的数据图和示意图大约只有十几到二十多张。经过 Native Candidate 过滤、VL Layout 判断和两路匹配以后最终保留下来的图片会明显减少主要集中在折线图柱状图饼图架构图流程图关键截图所以用户再问这份报告里有没有市场份额相关的图返回的应该是对应的市场份额饼图而不是页眉 Logo。这里真正减少的不是“图片数量”。而是没有检索价值的图片噪声。十、哪些 PDF 最适合这种处理方式比较典型的有三类。研报和分析报告图表非常密集很多核心结论就是通过折线图、柱状图和饼图表达的。用户可能直接问把这份报告里的市场规模趋势图找出来。如果知识库只保留文本这类信息在入库阶段就已经丢了。技术白皮书和产品文档系统架构图、部署图、流程图、数据流图往往比正文更直观。把架构图和附近的说明文字关联起来回答质量会明显不同。教材和操作手册示意图、产品截图、操作步骤图本身就是内容的一部分。用户检索到操作说明时如果能同时返回对应截图理解成本会低很多。反过来品牌宣传册这类“装饰驱动”的 PDF 就更难处理。大量全版背景图在视觉上可能也很像 figure但知识价值并不高。这类文档本身就需要更严格的语义过滤。十一、PDF 图片这一层做得对不对可以直接这样测和 Excel、合同一样比起问帮我总结这个 PDF。下面几类问题更容易暴露底层图片解析有没有真的做好。找图这份报告里有没有市场份额相关的图看返回的是数据图还是 Logo、页眉。图文关联这张架构图对应正文哪一段看图片和文本 Chunk 有没有真正关联。按内容找图把涉及收入增长趋势的图表找出来。看系统是不是把 figure 真正作为知识资产处理。扫描 PDF把这份扫描报告里的数据图表找出来。看系统返回的是局部图表还是直接扔回来一整页。来源追溯这个结论对应报告里的哪张图看回答能不能重新回到原始页面和图片。这些问题比“这个 PDF 一共抽出了多少张 JPG”更能判断整个链路有没有做好。十二、最后PDF 抽图难的不是 Extraction而是 Selection从 PDF 里把 image object 导出来本身并不是最难的部分。真正麻烦的是导出来以后你得知道哪些东西值得进入知识库。Logo 是图片。分割线可能也是图片。整页扫描件也是图片。数据图表、架构图、截图当然也是图片。但它们在知识库里的价值完全不同。所以在有谷大脑的 PDF 解析链路里图片提取不是一个孤立动作。整个链路更接近Native 结构解析负责找图片资源 → VL Layout 判断视觉区域 → IoU 做位置匹配 → 根据不同情况提取原图或裁剪 → 再把图片和 Page、Text Chunk、原始文档重新关联。最后我们真正关心的是用户问到某个问题时系统能不能把真正相关的那张原始图找回来并且知道它来自哪里。这和“这个 PDF 导出了多少张图片”是两件完全不同的事情。除了 PDF 图片有谷大脑也在针对 Excel、Word、PPT、合同等不同类型的企业文档做对应的解析和 Chunking。前面已经拆过Excel 表格进知识库为什么不能按行硬切合同做 RAG为什么不能直接按 Token 切后面还会继续写PDF 里的复杂表格怎么进知识库几百页 Word 制度文件怎么保留章节层级为什么 RAG 明明检索到了模型还是会答错多版本文档并存时怎么避免引用旧版本如果你也在做企业知识库、RAG、PDF 智能问答或企业 AI 落地可以关注后续更新。如果想进一步了解这些能力在产品里的实际应用可以体验有谷大脑https://brain.yogu.proPDF 抽图真正难的不是把图片拿出来而是知道哪些图值得被拿出来。
返回列表