Pārlūkot izejas kodu

feat(universal_doc_parser): enhance document processing with modular design and automatic table classification

- Introduced a modular framework allowing flexible replacement of processing components for various scenarios.
- Unified output format across different model combinations to ensure consistency in downstream processing.
- Added automatic table classification feature to distinguish between wired and wireless tables, improving recognition accuracy.
- Enhanced the main processing flow with detailed handling for both scanned documents and text PDFs, including fallback mechanisms for OCR.
- Updated documentation to reflect new features and configuration options.
zhch158_admin 2 dienas atpakaļ
vecāks
revīzija
83c6b132d5
1 mainītis faili ar 450 papildinājumiem un 141 dzēšanām
  1. 450 141
      docs/ocr_tools/universal_doc_parser/模型统一框架.md

+ 450 - 141
docs/ocr_tools/universal_doc_parser/模型统一框架.md

@@ -2,6 +2,32 @@
 
 参考 MinerU 实现的模型统一框架,针对金融场景设计。
 
+## 核心设计理念
+
+### 1. 模块化与可替换性
+框架采用**模块化设计**,各处理节点可根据不同场景灵活替换:
+- **方向识别**:支持多种模型(PP-LCNet、PDF rotation等)
+- **Layout检测**:支持 Docling、MinerU、Paddle、DiT 等多种检测器
+- **OCR识别**:支持 PaddleOCR
+- **表格识别**:支持 UNet(有线表格)、VLM(无线表格)等多种方案
+- **公式识别**:支持 MinerU VLM、PaddleOCR-VL 等
+
+通过配置文件(YAML)即可切换不同的模型组合,无需修改代码。
+
+### 2. 统一输出格式
+无论使用何种模型组合,**输出格式统一**,确保下游处理的一致性:
+- **统一内部描述结构**:`middle.json`(MinerU 标准格式)
+- **增强版格式**:`enhanced.json`(包含更多元数据)
+- **多格式输出**:JSON、Markdown、HTML 等
+- **坐标统一**:所有坐标统一转换回原图坐标系
+
+### 3. 场景适配
+针对不同业务场景(银行流水、财务报表等),提供预配置的配置文件:
+- 银行流水场景:`bank_statement_*.yaml`
+- 财务报表场景:可自定义配置
+- 支持有线/无线表格自动分类
+- 支持文字PDF和扫描件混合处理
+
 ## 支持场景
 
 | 场景类型 | 特点 | 表格形式 |
@@ -16,7 +42,8 @@
 | **方向分类** | PP-LCNet_x1_0_doc_ori | paddle onnx格式的模型 |
 | **版式检测** | Docling Layout / DocLayout-YOLO | Docling 或 MinerU 模型 |
 | **文字识别** | PaddleOCR (PyTorch) | 效果好,支持角度校正 |
-| **表格结构识别** | MinerU VLM / PaddleOCR-VL / UNET 有线表格 | VLM 返回 HTML 结构 |
+| **表格分类** | PaddleTableClsModel | 自动区分有线/无线表格 ⭐ 新增 |
+| **表格结构识别** | MinerU VLM / PaddleOCR-VL / UNET 有线表格 | VLM 返回 HTML 结构,UNet 返回单元格坐标 |
 | **公式识别** | MinerU VLM | 返回 LaTeX |
 | **单元格坐标匹配** | TableCellMatcher | OCR 检测框与 VLM 结构匹配 |
 
@@ -24,48 +51,47 @@
 
 ## 处理流程
 
-### 主流程图
+### 主流程图(简化版)
+
+主流程采用**模块化设计**,各处理节点可根据场景配置替换:
 
 ```mermaid
 graph TB
-    A[输入 PDF/图片] --> B[加载文档并分类]
-    
-    B --> C{文档类型?}
-    C -->|PDF| D[PDF分类: 扫描件/数字原生]
-    C -->|图片目录| E[加载所有图片]
-    
-    D --> F[处理每一页]
-    E --> F
-    
-    F --> G[页面方向识别<br/>仅扫描件]
-    G --> H[Layout 检测]
-    
-    H --> I[去重重叠框]
-    I --> J{大文本块转表格?}
-    J -->|启用| K[后处理转换]
-    J -->|否| L
-    K --> L[整页 OCR<br/>获取所有 text spans]
-    
-    L --> M[Span 去重与排序]
-    M --> N[Span-Block 匹配<br/>SpanMatcher]
+    A[输入 PDF/图片] --> B[文档加载与分类]
     
-    N --> O[元素分类]
-    O --> P[处理各类元素]
+    B --> C[逐页处理<br/>详见单页处理流程]
     
-    P --> Q[按阅读顺序排序]
-    Q --> R[坐标转换回原图]
+    C --> D[跨页表格合并]
     
-    R --> S{所有页处理完?}
-    S -->|否| F
-    S -->|是| T[跨页表格合并]
+    D --> E[统一输出格式<br/>JSON/Markdown/HTML]
     
-    T --> U[输出结果]
+    style C fill:#e1f5ff
+    style E fill:#fff4e1
     
-    style L fill:#e1f5ff
-    style N fill:#e1f5ff
-    style P fill:#fff4e1
+    classDef replaceable fill:#ffe1e1,stroke:#ff0000,stroke-width:2px
+    class B,C,D replaceable
 ```
 
+**关键特性**:
+- ✅ **模块化设计**:各处理节点可独立替换(见下方"可替换组件")
+- ✅ **统一输出格式**:无论使用何种模型组合,输出格式统一(见"输出格式说明")
+- ✅ **单页处理流程**:详见下方详细流程图
+
+**可替换组件**:
+- **方向识别**:PP-LCNet(扫描件) / PDF rotation(文字PDF)
+- **Layout检测**:Docling / MinerU / Paddle / DiT
+- **OCR识别**:PaddleOCR / MinerU OCR
+- **表格分类**:PaddleTableClsModel(可选)
+- **表格识别**:UNet(有线) / VLM(无线:MinerU VLM / PaddleOCR-VL)
+- **公式识别**:MinerU VLM / PaddleOCR-VL
+
+**统一输出格式**:
+- `{doc}_middle.json`:MinerU 标准格式(统一内部描述结构)
+- `{doc}_enhanced.json`:增强版格式(包含更多元数据)
+- `{doc}_page_XXX.json`:每页独立 JSON(包含单元格坐标)
+- `{doc}.md` / `{doc}_page_XXX.md`:Markdown 格式
+- `tables/*.html`:表格 HTML(带 data-bbox 坐标)
+
 ---
 
 ### 单页处理详细流程
@@ -75,17 +101,28 @@ graph TB
     A[输入:页面图像] --> B{PDF类型?}
     
     B -->|扫描件| C[页面方向识别<br/>PP-LCNet]
-    B -->|数字PDF| D
+    B -->|文字PDF| C1[获取PDF页面rotation<br/>转换为rotate_angle并旋转图像]
     C --> D[Layout 检测<br/>Docling/MinerU/DiT]
+    C1 --> D
     
     D --> E[去重重叠框<br/>IoU过滤]
     E --> F{大文本块转表格?}
     
     F -->|是| G[面积占比判断<br/>转换为table类型]
     F -->|否| H
-    G --> H[整页 OCR<br/>获取所有 text spans]
+    G --> H
+    
+    H --> H1{PDF类型?}
+    H1 -->|扫描件| H2[整页 OCR<br/>获取所有 text spans]
+    H1 -->|文字PDF| H3[PDF文本提取<br/>extract_all_text_blocks]
     
-    H --> I[Span 去重<br/>IoU过滤]
+    H3 --> H4{页面类型检测}
+    H4 -->|文字页| H5[使用PDF提取结果]
+    H4 -->|扫描页| H2
+    H3 -->|提取失败| H2
+    
+    H2 --> I[Span 去重<br/>IoU过滤]
+    H5 --> I
     I --> J[Span 排序<br/>从上到下、从左到右]
     J --> K[Span-Block 匹配<br/>overlap_threshold=0.5]
     
@@ -115,7 +152,8 @@ graph TB
     S --> T[按阅读顺序排序]
     T --> U[坐标转换回原图]
     
-    style H fill:#e1f5ff
+    style H2 fill:#e1f5ff
+    style H3 fill:#e1f5ff
     style K fill:#e1f5ff
     style L fill:#fff4e1
     style L1 fill:#fff4e1
@@ -126,37 +164,68 @@ graph TB
     style L6 fill:#fff4e1
 ```
 
-### 关键改进:整页 OCR + Span 匹配
+### 关键改进:整页 OCR/PDF提取 + Span 匹配
+
+参考 MinerU 的处理方式,新流程采用 **整页文本提取 → Span-Block 匹配** 策略:
+
+**处理路径**:
 
-参考 MinerU 的处理方式,新流程采用 **整页 OCR → Span-Block 匹配** 策略:
+1. **扫描件/图片**:
+   - **整页 OCR**:先对整个页面进行 OCR,获取所有 text spans(包含坐标和文本)
+   - 获取所有 OCR spans
 
-1. **整页 OCR**:先对整个页面进行 OCR,获取所有 text spans(包含坐标和文本)
-2. **Span 去重**:移除高 IoU 重叠的 spans,保留置信度高的
-3. **Span 排序**:按坐标排序(从上到下,从左到右),方便人工检查缺失字符
-4. **Span-Block 匹配**:将 OCR spans 按重叠比例(默认0.5)匹配到对应的 layout blocks
-5. **文本合并**:将匹配到同一 block 的 spans 按阅读顺序合并
+2. **文字PDF**:
+   - **PDF文本提取**:从PDF直接提取文本块(`extract_all_text_blocks`)
+   - **页面类型检测**:检测该页是否为扫描页(`detect_page_type`)
+     - 如果是文字页:使用PDF提取结果
+     - 如果是扫描页:fallback到OCR
+   - **提取失败时**:自动fallback到OCR
+
+**后续处理(统一)**:
+
+3. **Span 去重**:移除高 IoU 重叠的 spans,保留置信度高的
+4. **Span 排序**:按坐标排序(从上到下,从左到右),方便人工检查缺失字符
+5. **Span-Block 匹配**:将 spans 按重叠比例(默认0.5)匹配到对应的 layout blocks
+6. **文本合并**:将匹配到同一 block 的 spans 按阅读顺序合并
 
 **优势**:
 - ✅ 避免裁剪小图 OCR 失败的问题
 - ✅ OCR 可以利用更多上下文信息
 - ✅ 坐标更精确(整页坐标系)
 - ✅ 减少重复 OCR 调用,提高效率
+- ✅ **文字PDF优先使用PDF文本提取**,准确率更高,速度更快
+- ✅ **自动fallback机制**:PDF提取失败或检测到扫描页时自动使用OCR
 - ✅ 与 MinerU 处理方式一致
 
 **代码实现**:
 ```python
-# 1. 整页 OCR
-all_ocr_spans = self.ocr_recognizer.recognize_text(detection_image)
+# 1. 根据PDF类型选择文本提取方式
+if pdf_type == 'txt' and pdf_doc is not None:
+    # 文字PDF:从PDF提取文本块
+    actual_page_type = PDFUtils.detect_page_type(pdf_doc, page_idx)
+    if actual_page_type == 'txt':
+        all_text_spans, rotation = PDFUtils.extract_all_text_blocks(
+            pdf_doc, page_idx, scale=scale, return_upright_coords=True
+        )
+        all_text_spans = self._convert_pdf_blocks_to_spans(
+            all_text_spans, detection_image.shape
+        )
+    else:
+        # 扫描页,使用OCR
+        all_text_spans = self.ocr_recognizer.recognize_text(detection_image)
+else:
+    # 扫描件:整页 OCR
+    all_text_spans = self.ocr_recognizer.recognize_text(detection_image)
 
 # 2. 去除重复 spans
-all_ocr_spans = SpanMatcher.remove_duplicate_spans(all_ocr_spans)
+all_text_spans = SpanMatcher.remove_duplicate_spans(all_text_spans)
 
 # 3. 按坐标排序
-all_ocr_spans = self._sort_spans_by_position(all_ocr_spans)
+all_text_spans = self._sort_spans_by_position(all_text_spans)
 
-# 4. 将 OCR spans 匹配到 layout blocks
+# 4. 将 spans 匹配到 layout blocks
 matched_spans = SpanMatcher.match_spans_to_blocks(
-    all_ocr_spans, layout_results, overlap_threshold=0.5
+    all_text_spans, layout_results, overlap_threshold=0.5
 )
 
 # 5. 在元素处理时使用预匹配的 spans
@@ -172,6 +241,8 @@ element = self.element_processors.process_text_element(
 
 表格处理支持两种路径:**有线表格(UNET)** 和 **无线表格(VLM)**
 
+**新增功能**:支持自动表格分类,根据表格类型自动选择识别器
+
 ```mermaid
 graph TB
     A[表格区域] --> B[表格 OCR 预处理]
@@ -186,23 +257,31 @@ graph TB
         B5 --> B6
     end
     
-    B6 --> C{使用有线表格?}
+    B6 --> C{启用表格分类?}
+    
+    C -->|是| C1[表格分类器<br/>PaddleTableClsModel]
+    C1 --> C2{分类结果?}
+    C2 -->|wired| D[UNet 有线表格路径]
+    C2 -->|wireless| E[VLM 无线表格路径]
     
-    C -->|是| D[UNet 有线表格路径]
-    C -->|否| E[VLM 无线表格路径]
+    C -->|否| C3{手动配置?}
+    C3 -->|use_wired_unet=true| D
+    C3 -->|否| E
     
     subgraph 有线表格路径
         D --> D1[UNet 检测表格线<br/>横线 + 竖线]
         D1 --> D2{启用倾斜矫正?}
-        D2 -->|是| D3[Hough变换检测角度<br/>矫正图片和OCR坐标]
+        D2 -->|是| D3[基于Mask检测倾斜角度<br/>Hough变换 + 矫正图片和OCR坐标]
         D2 -->|否| D4
         D3 --> D4[网格恢复<br/>grid_recovery.py]
-        D4 --> D5[边缘过滤<br/>edge_margin=padding×upscale×1.2]
+        D4 --> D4a[连通域提取单元格<br/>OCR边缘补偿]
+        D4a --> D5[边缘过滤<br/>edge_margin=padding×upscale×1.2]
         D5 --> D6[文本填充<br/>text_filling.py]
-        D6 --> D7[生成HTML<br/>data-bbox属性]
-        D7 --> D8{识别成功?}
-        D8 -->|否| E[自动Fallback到VLM]
-        D8 -->|是| F
+        D6 --> D7[二次OCR修正<br/>单元格裁剪OCR]
+        D7 --> D8[生成HTML<br/>data-bbox属性]
+        D8 --> D9{识别成功?}
+        D9 -->|否| E[自动Fallback到VLM]
+        D9 -->|是| F
     end
     
     subgraph 无线表格路径
@@ -221,6 +300,26 @@ graph TB
     style E1 fill:#fff4e1
 ```
 
+#### 表格分类(可选)
+
+**配置项**:`table_classification.enabled: true`
+
+启用后,系统会自动对每个表格进行分类,判断是有线表格还是无线表格:
+
+1. **分类模型**:使用 MinerU 的 `PaddleTableClsModel`
+2. **分类结果**:
+   - `wired`:有线表格(带边框)→ 使用 UNet 识别
+   - `wireless`:无线表格(无边框)→ 使用 VLM 识别
+3. **辅助判断**:使用线条检测辅助判断
+   - 只有横线或只有竖线 → 强制判断为无线表格
+   - 无线条 → 判断为无线表格
+4. **置信度阈值**:`confidence_threshold: 0.5`(可配置)
+
+**优势**:
+- ✅ 自动选择最优识别器,无需手动配置
+- ✅ 提高识别准确率(有线表格用UNet,无线表格用VLM)
+- ✅ 支持混合场景(同一文档中同时存在有线/无线表格)
+
 #### 表格OCR预处理(共享逻辑)
 
 无论使用哪种表格识别方法,都需要先进行OCR预处理:
@@ -228,7 +327,7 @@ graph TB
 1. **裁剪表格区域**:添加 `padding=10px` 保护边缘内容
 2. **表格方向检测**:使用 PP-LCNet 检测并矫正表格方向
 3. **收集OCR框**:
-   - **优先**:使用整页OCR结果中与表格区域重叠的spans
+   - **优先**:使用整页OCR结果中与表格区域重叠的spans(仅当表格未旋转时)
    - **兜底**:对裁剪后的表格区域单独OCR
 4. **坐标转换**:将坐标从原图转换到裁剪后的表格图像坐标系
 
@@ -236,6 +335,7 @@ graph TB
 - padding=10px 在原图坐标系中
 - 表格图像的 (0,0) 对应原图的 (bbox[0]-padding, bbox[1]-padding)
 - UNet处理时会放大 upscale_ratio≈3.333 倍
+- **文字PDF支持**:对于文字PDF(`pdf_type='txt'`),会传递 `pdf_type` 参数,支持PDF字符提取作为OCR补充
 
 #### 有线表格识别流程(UNET)
 
@@ -248,13 +348,15 @@ graph TB
    - 坐标在放大后的图像坐标系(upscale≈3.333倍)
 
 2. **倾斜检测与矫正**(可选,`enable_deskew: true`):
-   - 使用 Hough 变换检测表格线倾斜角度
+   - **基于Mask的倾斜检测**:使用UNet检测的横线mask进行Hough变换,检测倾斜角度
    - 坐标系:Y轴向下,逆时针旋转为正角度
    - 矫正逻辑:`correction_angle = -detected_angle`(反向旋转)
    - 同步更新表格图像和OCR框坐标
+   - 矫正后重新运行UNet,确保mask与矫正后的图像对齐
 
 3. **网格恢复**(`grid_recovery.py`):
-   - 提取唯一的行线和列线坐标
+   - **连通域提取**:使用连通域法提取单元格(替代投影法)
+   - **OCR边缘补偿**:使用OCR框信息补偿边缘单元格,提高边缘单元格识别准确率
    - **边缘过滤**:过滤padding区域的噪声线条
      ```python
      edge_margin = int(crop_padding × upscale × 1.2)  # 例如:10 × 3.333 × 1.2 = 40px
@@ -263,30 +365,50 @@ graph TB
    - 生成单元格网格
 
 4. **文本填充**(`text_filling.py`):
-   - 计算OCR框与单元格的IoU
+   - 计算OCR框与单元格的中心点匹配
    - 匹配OCR文本到对应单元格
    - 支持置信度过滤(`ocr_conf_threshold`)
 
-5. **HTML生成**:
+5. **二次OCR修正**(`text_filling.py`):
+   - **总是执行**,不区分PDF类型
+   - 对单元格进行裁剪OCR,补充或修正文本
+   - 处理空文本单元格、低置信度文本、OCR误合并等情况
+   - 对于文字PDF(`pdf_type='txt'`),空文本单元格不触发二次OCR,为了解决文字PDF中误合并问题
+
+6. **HTML生成**:
    - 生成标准表格HTML
    - 添加 `data-bbox` 属性记录单元格坐标
 
-6. **坐标逆转换**:
+7. **坐标逆转换**:
    - 将所有坐标从裁剪+放大坐标系转换回原图坐标系
+   - 如果进行了倾斜矫正,需要逆向旋转坐标
 
-7. **自动Fallback**:
-   - 如果有线识别失败(返回空HTML),自动切换到VLM识别
+8. **自动Fallback**:
+   - 如果有线识别失败(返回空HTML或空cells),自动切换到VLM识别
    - 无需手动干预,确保识别鲁棒性
 
+**文字PDF支持**:
+- 支持传递 `pdf_type='txt'` 参数到有线表格识别器
+- 二次OCR修正,处理空文本单元格、低置信度文本、OCR误合并等情况
+- 对于文字PDF(`pdf_type='txt'`),空文本单元格不触发二次OCR,为了解决文字PDF中误合并问题
+
 **关键配置**:
 ```yaml
+# 表格分类配置(推荐启用)
+table_classification:
+  enabled: true                 # 启用自动表格分类
+  module: "paddle"              # 使用 PaddleTableClsModel
+  confidence_threshold: 0.5     # 分类置信度阈值
+
+# 有线表格识别配置
 table_recognition_wired:
   use_wired_unet: true          # 启用有线表格
   upscale_ratio: 3.333          # 固定放大比例
-  enable_deskew: true           # 启用倾斜矫正
+  enable_deskew: true           # 启用倾斜矫正(基于Mask检测)
   row_threshold: 10             # 行合并阈值(像素)
   col_threshold: 15             # 列合并阈值(像素)
   ocr_conf_threshold: 0.8       # OCR置信度阈值
+  use_custom_postprocess: true  # 使用自定义后处理(支持OCR边缘补偿)
 ```
 
 #### 无线表格识别流程(VLM)
@@ -439,10 +561,15 @@ def process_text_element(
 
 | 处理阶段 | 方向识别 | 建议 |
 |---------|---------|------|
-| **页面级** | PP-LCNet | 可配置,扫描件开启,数字PDF关闭 |
+| **页面级** | 扫描件:PP-LCNet<br/>文字PDF:PDF rotation | 扫描件使用PP-LCNet模型识别<br/>文字PDF从PDF元数据获取rotation并旋转图像 |
 | **表格区域** | - | 可选,VLM 有一定容忍度,OCR 自带角度校正 |
 | **文本区域** | - | 不需要,OCR 自带校正 |
 
+**文字PDF方向处理**:
+- 从PDF页面元数据获取 `rotation` 角度
+- 转换为统一的 `rotate_angle` 定义(图像需要逆时针旋转的角度)
+- 旋转图像为正视方向,确保后续Layout检测和文本提取的准确性
+
 ---
 
 ## Layout 后处理
@@ -473,15 +600,21 @@ layout:
 
 | PDF 类型 | 文字块处理 | 表格处理 |
 |---------|-----------|---------|
-| **扫描件/图片** | 整页 OCR → Span 匹配 | OCR 检测(坐标) + VLM(结构) |
-| **数字原生 PDF** | 整页 OCR → Span 匹配 / PDF 字符提取 | OCR 检测(坐标) + VLM(结构) |
+| **扫描件/图片** | 整页 OCR → Span 匹配 | OCR 检测(坐标) + 表格分类 → UNet/VLM(结构) |
+| **数字原生 PDF(文字PDF)** | 整页 OCR → Span 匹配 / PDF 字符提取 | OCR 检测(坐标) + 表格分类 → UNet/VLM(结构)<br/>+ 单元格OCR修正(PDF字符提取优先) |
 
 **关键点**:
 - **整页 OCR 优先**:先对整页进行 OCR,再将结果匹配到 layout blocks
 - 数字原生 PDF 在 spans 匹配失败时,会尝试 PDF 字符提取
 - **表格处理无论 PDF 类型都需要 OCR 检测**,用于获取单元格内文本的精确坐标
-- VLM 只返回表格结构(HTML),不返回单元格坐标,需要与 OCR 检测结果匹配
-- 当前实现仅使用 VLM(MinerU VLM 或 PaddleOCR-VL)进行表格结构识别
+- **表格分类**:支持自动分类(有线/无线),自动选择最优识别器
+- **有线表格(UNet)**:
+  - 支持文字PDF,在二次OCR修正时优先使用PDF字符提取
+  - 支持OCR边缘补偿,提高边缘单元格识别准确率
+  - 识别失败时自动fallback到VLM
+- **无线表格(VLM)**:
+  - VLM 只返回表格结构(HTML),不返回单元格坐标
+  - 需要与 OCR 检测结果匹配(TableCellMatcher)
 
 ### OCR 参数配置
 
@@ -538,6 +671,9 @@ ocr:
 
 ```
 universal_doc_parser/
+├── __init__.py
+├── main_v2.py # 命令行入口 ⭐
+│
 ├── config/ # 配置文件
 │ ├── bank_statement_yusys_v2.yaml # 银行流水配置(Docling + PaddleOCR-VL)
 │ ├── bank_statement_mineru_v2.yaml # 银行流水配置(MinerU layout + MinerU VLM)
@@ -557,15 +693,17 @@ universal_doc_parser/
 ├── models/ # 模型适配器
 │ └── adapters/
+│   ├── __init__.py
 │   ├── base.py # 适配器基类
 │   ├── mineru_adapter.py # MinerU 适配器
 │   ├── paddle_vl_adapter.py # PaddleOCR-VL 适配器
 │   ├── paddle_layout_detector.py # PaddleX RT-DETR 布局检测器
+│   ├── paddle_table_classifier.py # Paddle表格分类器 ⭐ 新增
 │   ├── docling_layout_adapter.py # Docling 布局检测器 ⭐
 │   ├── dit_layout_adapter.py # DiT 布局检测器 ⭐ 新增
 │   ├── mineru_wired_table.py # MinerU 有线表格识别器 ⭐ 新增
 │   └── wired_table/ # 有线表格子模块 ⭐ 新增
-│     ├── init.py
+│     ├── __init__.py
 │     ├── debug_utils.py # 调试工具
 │     ├── ocr_formatter.py # OCR 格式转换
 │     ├── skew_detection.py # 倾斜检测与矫正
@@ -573,16 +711,31 @@ universal_doc_parser/
 │     ├── text_filling.py # 文本填充
 │     ├── html_generator.py # HTML 生成
 │     └── visualization.py # 可视化
-│  
+│
+├── dit_support/ # DiT 布局检测器支持模块 ⭐
+│ ├── configs/ # DiT 配置文件
+│ │ ├── Base-RCNN-FPN.yaml
+│ │ └── cascade/
+│ │   └── cascade_dit_large.yaml
+│ ├── ditod/ # DiT 模型实现
+│ │ ├── __init__.py
+│ │ ├── backbone.py
+│ │ ├── beit.py
+│ │ ├── config.py
+│ │ └── deit.py
+│ └── README.md
+│
 ├── utils/ # 输出工具模块(已迁移到 ocr_utils)⚠️
-│ └── init.py # 仅作重新导出接口
-│  
-├── tests/ # 测试模块
-│ ├── test_skew_correction.py # 倾斜矫正测试
-│ └── ...
-│  
-├── main_v2.py # 命令行入口 ⭐
-└── 模型统一框架.md # 本文档
+│ └── __init__.py # 仅作重新导出接口
+│
+└── tests/ # 测试模块
+  ├── test_dit_layout_adapter.py # DiT 布局检测器测试
+  ├── test_doclayoutyolo.py # DocLayout-YOLO 测试
+  ├── test_layout_detector.py # 布局检测器测试
+  ├── test_pdf_rotation.py # PDF 旋转测试
+  ├── test_skew_correction.py # 倾斜矫正测试
+  ├── test_table_routing.py # 表格路由测试
+  └── *.png # 测试图片文件
 ```
 
 ---
@@ -609,7 +762,7 @@ python main_v2.py -i doc.pdf -c config/bank_statement_yusys_v2.yaml -o ./my_outp
 
 ```python
 from core.pipeline_manager_v2 import EnhancedDocPipeline
-from utils import OutputFormatterV2
+from ocr_utils import OutputFormatterV2  # 从 ocr_utils 导入
 
 # 初始化流水线
 with EnhancedDocPipeline("config/bank_statement_yusys_v2.yaml") as pipeline:
@@ -650,31 +803,51 @@ python main_v2.py -i large_document.pdf -c config.yaml --streaming -o ./output
 
 ---
 
-## 输出文件说明
-
-| 输出文件 | 说明 |
-|---------|------|
-| `{doc}_middle.json` | MinerU 标准格式 JSON |
-| `{doc}_enhanced.json` | 增强版 JSON(包含更多元数据)⭐ 新增 |
-| `{doc}_page_001.json` | 每页独立 JSON(包含单元格坐标) |
-| `{doc}_pdf_page_001.png` | PDF转换的页面图片 ⭐ 新增 |
-| `{doc}.md` | 完整文档 Markdown |
-| `{doc}_page_001.md` | 每页独立 Markdown(带坐标注释) |
-| `tables/*.html` | 表格 HTML 文件(带 data-bbox 坐标) |
-| `images/` | 提取的图片元素 |
-| `{doc}_page_001_layout.png` | Layout 可视化图片(debug 模式) |
-| `{doc}_page_001_ocr.png` | OCR 可视化图片(debug 模式) |
-| `{doc}_page_001_table_001_lines.png` | 有线表格线可视化 ⭐ 新增(wired debug) |
-| `{doc}_page_001_table_001_grid.png` | 有线表格网格结构 ⭐ 新增(wired debug) |
-| `{doc}_page_001_table_001_text.png` | 有线表格文本覆盖 ⭐ 新增(wired debug) |
-| `{doc}_page_001_table_001_components.png` | 有线表格连通域 ⭐ 新增(wired debug) |
-| `*_original.*` | 标准化前的原始文件(如有修改) |
+## 输出格式说明(统一描述格式)
+
+**核心原则**:无论使用何种模型组合,输出格式统一,确保下游处理的一致性。
+
+### 主要输出文件
+
+| 输出文件 | 格式说明 | 用途 |
+|---------|---------|------|
+| `{doc}_middle.json` | **MinerU 标准格式**(统一内部描述结构) | 标准输出,兼容 MinerU 生态 |
+| `{doc}_enhanced.json` | 增强版 JSON(包含更多元数据)⭐ | 包含识别方法、置信度等详细信息 |
+| `{doc}_page_001.json` | 每页独立 JSON(包含单元格坐标) | 按页输出,包含精确坐标信息 |
+| `{doc}.md` | 完整文档 Markdown | 人类可读格式 |
+| `{doc}_page_001.md` | 每页独立 Markdown(带坐标注释) | 按页 Markdown,便于检查 |
+| `tables/*.html` | 表格 HTML(带 `data-bbox` 坐标) | 表格结构化输出,包含单元格坐标 |
+| `images/` | 提取的图片元素 | 图片资源 |
+
+### 统一格式特点
+
+1. **坐标统一**:所有坐标统一转换回**原图坐标系**,确保一致性
+2. **结构统一**:无论使用何种识别方法,输出结构统一
+3. **元数据完整**:包含识别方法、置信度、处理时间等元数据
+4. **多格式支持**:同时输出 JSON、Markdown、HTML 等多种格式
+
+### 调试输出文件(可选)
+
+| 输出文件 | 说明 | 启用条件 |
+|---------|------|---------|
+| `{doc}_pdf_page_001.png` | PDF转换的页面图片 | `output.save_pdf_images: true` |
+| `{doc}_page_001_layout.png` | Layout 可视化图片 | `output.save_layout_image: true` |
+| `{doc}_page_001_ocr.png` | OCR 可视化图片 | `output.save_ocr_image: true` |
+| `{doc}_page_001_table_001_lines.png` | 有线表格线可视化 | `table_recognition_wired.debug_options.enabled: true` |
+| `{doc}_page_001_table_001_grid.png` | 有线表格网格结构 | `table_recognition_wired.debug_options.enabled: true` |
+| `{doc}_page_001_table_001_text.png` | 有线表格文本覆盖 | `table_recognition_wired.debug_options.enabled: true` |
+| `{doc}_page_001_table_001_components.png` | 有线表格连通域 | `table_recognition_wired.debug_options.enabled: true` |
+| `{doc}_page_001_table_001_paddle_table_lines.png` | 表格分类线条检测可视化 | `table_classification.debug_options.enabled: true` |
 
 **有线表格调试输出说明**:
 - 当配置 `table_recognition_wired.debug_options.enabled: true` 时,会生成详细的可视化图片
 - 这些图片帮助理解表格识别的各个处理阶段(表格线提取、网格恢复、文本填充等)
 - 详细说明请参考:[有线表格识别技术文档.md](有线表格识别技术文档.md)
 
+**表格分类调试输出说明**:
+- 当配置 `table_classification.debug_options.enabled: true` 时,会生成表格线检测可视化图片
+- 用于理解分类器如何判断表格类型(有线/无线)
+
 ---
 
 ## 配置说明
@@ -717,6 +890,31 @@ ocr_recognition:
   module: "mineru"
   language: "ch"
 
+# 表格分类配置(自动区分有线/无线表格)
+table_classification:
+  enabled: true               # 是否启用自动表格分类(默认关闭,使用手动配置)
+  module: "paddle"            # 分类模型:paddle(MinerU PaddleTableClsModel)
+  confidence_threshold: 0.5   # 分类置信度阈值
+  batch_size: 16              # 批处理大小
+  debug_options:
+    enabled: false            # 是否开启调试可视化输出
+    save_table_lines: true    # 保存表格线可视化
+
+# 有线表格识别配置
+table_recognition_wired:
+  use_wired_unet: true        # 是否启用有线表格识别
+  upscale_ratio: 3.333        # 放大比例
+  enable_deskew: true         # 是否启用倾斜矫正
+  row_threshold: 10           # 行合并阈值(像素)
+  col_threshold: 15           # 列合并阈值(像素)
+  ocr_conf_threshold: 0.8     # OCR置信度阈值
+  debug_options:
+    enabled: false            # 是否开启调试可视化输出
+    save_table_lines: true    # 保存表格线可视化
+    save_connected_components: true  # 保存连通域提取的单元格图
+    save_grid_structure: true  # 保存逻辑网格结构
+    save_text_overlay: true   # 保存文本填充覆盖图
+
 # 输出配置
 output:
   create_subdir: false        # 是否创建子目录
@@ -730,9 +928,15 @@ output:
 
 ---
 
-## 支持的布局检测器
+## 可替换组件说明
+
+框架采用**适配器模式**,各组件可根据场景灵活替换。通过修改配置文件即可切换,无需修改代码。
+
+### 布局检测器(Layout Detection)
 
-### 1. Docling Layout (推荐)
+支持多种布局检测模型,通过 `layout_detection.module` 配置切换:
+
+#### 1. Docling Layout (推荐)
 
 基于 HuggingFace transformers 的 RT-DETR 模型。
 
@@ -749,7 +953,7 @@ layout_detection:
 - `ds4sd/docling-layout-egret-medium`
 - `ds4sd/docling-layout-egret-large`
 
-### 2. PaddleX RT-DETR (ONNX)
+#### 2. PaddleX RT-DETR (ONNX)
 
 基于 ONNX Runtime 的 PaddleX 布局检测器。
 
@@ -760,7 +964,7 @@ layout_detection:
   model_dir: "/path/to/RT-DETR-H_layout_17cls.onnx"
 ```
 
-### 3. MinerU DocLayout-YOLO
+#### 3. MinerU DocLayout-YOLO
 
 MinerU 内置的布局检测模型。
 
@@ -770,7 +974,7 @@ layout_detection:
   model_name: "layout"
 ```
 
-### 4. DiT Layout (Document Image Transformer)
+#### 4. DiT Layout (Document Image Transformer)
 
 基于 Detectron2 的 DiT 模型,在 PubLayNet 数据集上训练。
 
@@ -782,18 +986,67 @@ layout_detection:
   device: "cpu"
   conf: 0.3
 ```
-支持类别:
 
-text:正文文本
-title:标题
-list:列表
-table:表格
-figure:图片/图表
-特点:
+**支持类别**:text、title、list、table、figure
 
-基于 Vision Transformer 架构
-适合学术文档和出版物
-需要 Detectron2 框架支持
+**特点**:基于 Vision Transformer 架构,适合学术文档和出版物
+
+---
+
+### OCR识别器(OCR Recognition)
+
+通过 `ocr_recognition.module` 配置切换:
+
+- **MinerU OCR**:`module: "mineru"`
+- **PaddleOCR**:`module: "paddle"`(需配置模型路径)
+
+---
+
+### 表格识别器(Table Recognition)
+
+#### 表格分类器(可选)
+
+通过 `table_classification.module` 配置:
+
+- **PaddleTableClsModel**:`module: "paddle"`(自动区分有线/无线表格)
+
+#### 有线表格识别
+
+通过 `table_recognition_wired.use_wired_unet` 配置:
+
+- **UNet 有线表格**:`use_wired_unet: true`(MinerU UNet模型)
+
+#### 无线表格识别
+
+通过 `vl_recognition.module` 配置:
+
+- **MinerU VLM**:`module: "mineru"`
+- **PaddleOCR-VL**:`module: "paddle"`(需配置服务地址)
+
+**后端支持**:
+- `backend: "http-client"`:HTTP 客户端
+- `backend: "vllm-engine"`:vLLM 引擎
+- `backend: "transformers"`:Transformers 库
+
+---
+
+### 公式识别器(Equation Recognition)
+
+通过 `vl_recognition.module` 配置(与无线表格共享):
+
+- **MinerU VLM**:`module: "mineru"`
+- **PaddleOCR-VL**:`module: "paddle"`
+
+---
+
+### 方向识别器(Orientation Classification)
+
+- **扫描件**:PP-LCNet(`preprocessor.module: "mineru"`)
+- **文字PDF**:自动从PDF元数据获取rotation(无需配置)
+
+---
+
+**配置示例**:见 `config/bank_statement_*.yaml` 文件
 
 ---
 
@@ -821,7 +1074,8 @@ figure:图片/图表
 - 页面方向识别
 - Layout 检测与去重
 - **整页 OCR + Span-Block 匹配** ⭐
-- 元素分类处理
+- **表格自动分类**(可选)⭐ 新增
+- 元素分类处理(支持智能选择表格识别器)
 - 阅读顺序排序
 - 坐标转换
 
@@ -837,15 +1091,33 @@ OCR Span 与 Layout Block 匹配器,参考 MinerU 实现:
 
 元素处理器,处理不同类型的元素:
 - `process_text_element()` - 文本处理(支持 pre_matched_spans)
-- `process_table_element()` - 表格处理(VLM + OCR 坐标匹配)
+- `process_table_element_wired()` - 有线表格处理(UNet + OCR 坐标匹配,支持文字PDF)
+- `process_table_element_vlm()` - 无线表格处理(VLM + OCR 坐标匹配)
 - `process_image_element()` - 图片处理
 - `process_equation_element()` - 公式处理
 - `process_code_element()` - 代码处理
 - `process_discard_element()` - 丢弃元素处理(支持 pre_matched_spans)
 
-### 3. OutputFormatterV2 (`output_formatter_v2.py`)
+### 3.1. PaddleTableClassifier (`paddle_table_classifier.py`) ⭐ 新增
 
-统一输出格式化器:
+表格分类器,自动区分有线表格和无线表格:
+- `classify()` - 分类单个表格图像
+- `batch_classify()` - 批量分类表格图像
+- 使用 MinerU 的 `PaddleTableClsModel` 进行分类
+- 支持线条检测辅助判断(只有横线或竖线时强制判断为无线表格)
+
+### 3.1. PaddleTableClassifier (`paddle_table_classifier.py`) ⭐ 新增
+
+表格分类器,自动区分有线表格和无线表格:
+- `classify()` - 分类单个表格图像
+- `batch_classify()` - 批量分类表格图像
+- 使用 MinerU 的 `PaddleTableClsModel` 进行分类
+- 支持线条检测辅助判断(只有横线或竖线时强制判断为无线表格)
+- 输出分类结果:`wired`(有线表格)或 `wireless`(无线表格)
+
+### 4. OutputFormatterV2 (来自 `ocr_utils`)
+
+统一输出格式化器,位于 `ocr_utils` 包中:
 - MinerU 标准 middle.json 格式
 - 每页独立 JSON(含单元格坐标)
 - Markdown 输出(完整版 + 按页)
@@ -853,7 +1125,12 @@ OCR Span 与 Layout Block 匹配器,参考 MinerU 实现:
 - 可视化图片(Layout/OCR)
 - 金额数字标准化
 
-### 4. TableCellMatcher (来自 `merger`)
+**导入方式**:
+```python
+from ocr_utils import OutputFormatterV2
+```
+
+### 5. TableCellMatcher (来自 `merger`)
 
 表格单元格坐标匹配器:
 - 使用动态规划进行行内单元格匹配
@@ -871,7 +1148,7 @@ OCR Span 与 Layout Block 匹配器,参考 MinerU 实现:
 - `mineru.model.ocr` - OCR 模型
 - `mineru.model.ori_cls` - 方向分类模型
 
-### OCR Tools 组件(来自 ocr_tools.ocr_merger)⚠️
+### OCR Tools 组件(来自 `ocr_tools.ocr_merger`)⚠️
 
 实际导入路径(**注意:不是 ocr_verify**):
 
@@ -883,29 +1160,61 @@ from ocr_tools.ocr_merger import TableCellMatcher, TextMatcher
 ├── table_cell_matcher.py  # 单元格坐标匹配
 ├── text_matcher.py        # 文本匹配
 └── merger_core.py         # 核心匹配算法
-````
-功能说明:
+```
+
+**功能说明**:
+- `TableCellMatcher`:将 OCR 检测框与 VLM 表格结构匹配,使用动态规划算法
+- `TextMatcher`:文本相似度匹配工具
+
+### OCR Utils 工具包(`ocr_utils`)⭐
+
+**定位**:统一的OCR工具包,提供文档处理相关的工具函数,支持跨项目复用。
+
+**主要模块**:
 
-TableCellMatcher:将 OCR 检测框与 VLM 表格结构匹配,使用动态规划算法
-TextMatcher:文本相似度匹配工具
+| 模块 | 功能 | 说明 |
+|------|------|------|
+| `OutputFormatterV2` | 统一输出格式化器 | 生成 JSON、Markdown、HTML 等格式 |
+| `JSONFormatters` | JSON 格式化工具 | 格式化 MinerU 标准 JSON、增强 JSON 等 |
+| `MarkdownGenerator` | Markdown 生成器 | 生成完整文档和按页 Markdown |
+| `HTMLGenerator` | HTML 生成器 | 生成表格 HTML(带 data-bbox 坐标) |
+| `VisualizationUtils` | 可视化工具 | Layout、OCR 可视化图片生成 |
+| `normalize_financial_numbers` | 金额标准化 | 金融数字标准化(金额、百分比等) |
+| `PDFUtils` | PDF 处理工具 | PDF 文本提取、坐标转换等 |
+| `BBoxExtractor` | 边界框提取器 | 从 HTML 等格式提取边界框 |
+| `file_utils` | 文件处理工具 | 文件列表处理、PDF 转图片等 |
+| `image_utils` | 图像处理工具 | 图像解码、预处理、坐标转换等 |
+| `html_utils` | HTML 处理工具 | HTML 表格解析、图片处理等 |
+| `number_utils` | 数字解析工具 | 数字解析和标准化 |
 
-o工具模块(已迁移到 ocr_utils)⚠️
-输出工具已统一迁移到 ocr_utils 包,
+**导入示例**:
 ```python
-# 从 ocr_utils 重新导出
+# 主要输出工具
 from ocr_utils import (
-    OutputFormatterV2,       # 统一输出格式化器
-    JSONFormatters,          # JSON格式化
-    MarkdownGenerator,       # Markdown生成
-    HTMLGenerator,           # HTML生成
-    VisualizationUtils,      # 可视化工具
-    normalize_financial_numbers,  # 金额标准化
+    OutputFormatterV2,           # 统一输出格式化器
+    JSONFormatters,              # JSON格式化
+    MarkdownGenerator,           # Markdown生成
+    HTMLGenerator,               # HTML生成
+    VisualizationUtils,          # 可视化工具
+    normalize_financial_numbers, # 金额标准化
+)
+
+# PDF 工具(延迟导入)
+from ocr_utils import PDFUtils, BBoxExtractor
+
+# 文件工具
+from ocr_utils import (
+    get_input_files,
+    convert_pdf_to_images,
+    parse_page_range
 )
 ```
-优势:
-  . 统一管理所有输出工具
-  . 跨项目复用代码
-  . 更好的版本控制
+
+**优势**:
+- ✅ **统一管理**:所有输出工具集中管理,避免代码重复
+- ✅ **跨项目复用**:可在多个 OCR 相关项目中复用
+- ✅ **版本控制**:独立版本管理,便于维护和升级
+- ✅ **延迟导入**:PDF 相关工具支持延迟导入,避免依赖问题
 
 其他依赖
   . transformers - Docling 模型加载