尧图网站设计 尧图网站设计YAOTU DESIGN
ARTICLE DETAIL

资讯详情

深耕网站设计与一线实操的经验洞察。

PlanSightRAG:Visual-First多模态RAG实现工程图纸问答与合规审查

PlanSightRAG:Visual-First多模态RAG实现工程图纸问答与合规审查 图纸合规审查一直是工程设计与管理中的难题。传统方式是人工翻阅图纸和规范条文逐条比对效率低、易漏检而且对审查人的经验要求很高。随着多模态大模型和检索增强生成RAG技术的成熟很多团队开始尝试用 AI 辅助完成图纸问答与合规检查。最近我在研究 PlanSightRAG 这个方案——一个面向民用标准图纸的 Visual-First 多模态 RAG 系统目标是自动化完成图纸问答和合规性检查。这篇文章我会从问题背景、方案设计、核心模块、代码实现、排查思路和工程落地建议几个方面完整拆解 PlanSightRAG 的实现过程。内容偏实战既有概念讲解也有可参考的代码流程适合正在做多模态 RAG、文档问答、图纸智能审核方向的开发者。先看一个实际的工程痛点一张建筑平面图里包含了墙体、门窗、疏散通道、防火分区、设备布局等信息而对应规范可能分散在十几本标准中。要让模型回答“这个房间的疏散门是否满足开启方向要求”模型不仅需要看懂图纸上的图形符号还要结合规范条文的语义约束进行推理。这不是普通文本 RAG 能解决的它要求系统同时处理视觉元素、空间关系和规范文本PlanSightRAG 就是围绕这个目标设计的。1. PlanSightRAG 要解决什么问题1.1 图纸问答为什么比文本问答难传统 RAG 系统处理的是纯文本数据把文档切块、向量化、检索、拼接上下文、生成答案。这条链路在文本域已经很成熟但对工程图纸几乎不适用。原因有三点首先图纸的核心信息在视觉层。墙体厚度、门的位置、疏散通道宽度、设备间距这些信息以图形和标注形式存在不是自然语言句子。如果只做 OCR 文字提取会丢失大量空间关系和图形语义。其次图纸问答需要“看图说话”和“对照规范”同时进行。用户问“该区域的疏散距离是否达标”模型必须先定位到对应区域读取图上标注的尺寸再匹配规范中的限值最后给出是否合规的判断。这个链路跨越了视觉理解、信息抽取和规则匹配三个阶段。最后工程图纸专业性强通用 VQA视觉问答模型无法胜任。通用模型能识别“图片里有什么”但不知道“建筑防火规范里疏散距离是多少”更不知道“图纸里某个标注对应哪个构件”。所以必须有外部知识注入这正是 RAG 的用武之地。1.2 合规检查从“找条文”到“做判断”合规检查比问答更进一步。问答要求模型给出信息合规检查要求模型给出判断和依据。PlanSightRAG 在设计上把这两者统一在一个 Pipeline 里对普通问题回答即可对合规类问题必须在回答中附带规范依据、位置定位和判定逻辑。这意味着系统不能只做相似度检索还要有规则引擎或结构化判定模块输出结果需要可追溯、可复核。1.3 PlanSightRAG 的核心设计思想Visual-FirstVisual-First 指的是在系统链路中视觉理解不是可选的预处理步骤而是整个流程的主干。具体表现为图纸首先经过多模态解析得到结构化的视觉元素构件、标注、区域。视觉元素与规范文本统一映射到一个混合检索空间。生成阶段利用多模态大模型同时接收图像块、文本片段和结构化信息完成推理。这种设计与传统“先 OCR 再文本 RAG”的路线有本质区别。视觉信息不是辅助而是检索和推理的主要对象。2. 多模态 RAG 技术基础2.1 从 RAG 到多模态 RAG标准 RAG 的流程是文档加载 → 文本切块 → 向量化 → 检索 → 重排 → 生成多模态 RAG 在此基础上增加了两种能力文档中的图像可以被解析、向量化并参与检索生成阶段可以输入图像或图像摘要而不是只有文本。目前业界常见做法有三种第一解析式多模态 RAG。先通过多模态模型把图片内容转成文本描述caption再走文本 RAG。优点是实现简单缺点是信息损失大尤其是图纸这种高密度图形。第二原生多模态 RAG。图片和文本分别向量化使用多模态 Embedding 模型统一映射到向量空间。检索时输入文本和图像一起返回 Top-K。这种方式更接近“多模态语义检索”的理想状态但对模型和算力要求高。第三混合式多模态 RAGPlanSightRAG 采用的方式。视觉解析、文本解析、规则引擎并行各自产出结构化结果最后在生成阶段融合。这种方式最适合工程类强逻辑场景因为合规检查不能只靠语义相似度还需要规则匹配。2.2 工程图纸场景下的 Embedding 选择工程图纸的向量化核心难点在于“图形符号”与“自然语言规范”之间的语义鸿沟。通用文本 Embedding 模型无法直接处理图纸。目前可行的方案有两种一种是区域图像 Embedding。把图纸按网格或语义区域裁切成图像块用 CLIP 类模型或专门训练的建筑图纸 Embedding 模型进行向量化。这种方式能保留视觉局部特征检索时以图搜图。另一种是符号级结构化表示。先通过目标检测模型识别图中的构件门、窗、消火栓、疏散指示等生成结构化 JSON 描述再将该描述文本化后送入文本 Embedding 模型。这种方式检索精度高但依赖检测模型的完整度。PlanSightRAG 的实践里建议两者结合图像块用于召回结构化符号用于过滤和验证。后面代码部分会详细说明。3. PlanSightRAG 架构详解3.1 总体架构整个系统按照数据流向分成五个核心层图纸输入 ↓ [视觉解析引擎] --- 构件检测 / 区域分割 / 标注提取 ↓ [结构化中间表示] --- 区域、构件、文本标注、坐标 ↓ [混合索引与检索] --- 图像块向量 文本向量 规则标签 ↓ [多模态融合生成] --- 检索结果 规范条文 图像块 → LLM ↓ [合规判定与溯源] --- 规则引擎校验 / 输出依据3.2 五层核心模块第一层视觉解析引擎负责把 PDF 或图片格式的图纸解析成结构化数据。关键技术包括矢量解析从 CAD 导出的 PDF 往往保留矢量信息可以直接提取线条、文字、图块。目标检测对栅格化后的图纸做构件级识别常用 YOLO 类模型。OCR 标注抽取识别图纸中的尺寸、房间名、防火分区编号等。输出统一为 JSON 格式包含构件类型、坐标、尺寸、关联属性。第二层结构化中间表示这一层是 PlanSightRAG 的“语义枢纽”。它的核心是把分散的图纸元素组织成可检索的结构。例如{ region_id: A-01, region_type: 疏散走道, elements: [ {type: door, id: D-102, width_mm: 1200, swing: 向外}, {type: sign, text: 安全出口, direction: 左侧} ], relations: [ {from: D-102, to: 安全出口, relation: 指向} ] }结构化层的作用是让后续检索和规则判断不再依赖“重新读图”。第三层混合索引与检索将图像块、结构化 JSON、规范文本分别索引图像索引区域裁切图 → 图像向量。文本索引规范条文 → 文本向量。标签索引构件类型、规范编号、区域功能 → 倒排索引。查询时三个索引并行检索再通过融合排序得到候选集。第四层多模态融合生成把候选图像块、结构化信息、规范条文、用户问题拼接成 Prompt交给多模态 LLM 生成答案。融合的关键在于让模型看到图、看到数据、看到条文三者在上下文中对齐。第五层合规判定与溯源合规问题不能只靠 LLM“感觉”。需要在提示词之外增加规则校验层例如数值比较规则疏散距离是否超过规范限值。逻辑判断规则门的开启方向是否与疏散方向一致。枚举校验规则构件类型是否在允许清单内。输出包含判定结果、涉及区域、涉及构件、对应规范条文形成可追溯的审查记录。4. 核心 Pipeline 实操拆解下面进入代码部分。我会用 Python 描述一个可运行的 PlanSightRAG 精简版流程重点展示思路。实际生产环境需要根据你的数据格式、模型部署方式做调整。4.1 构建项目结构plansightrag-demo/ ├── config/ │ └── settings.yaml ├── data/ │ ├── plans/ │ │ └── demo_floor_plan.pdf │ └── regulations/ │ └── fire_code.md ├── src/ │ ├── visual_parser.py │ ├── struct_index.py │ ├── hybrid_retriever.py │ ├── multimodal_fusion.py │ ├── compliance_engine.py │ └── pipeline.py ├── output/ │ └── audit_report.json └── requirements.txt4.2 定义配置文件先创建一个简单的配置文件把关键参数集中管理。# config/settings.yaml model: visual_detector: yolov8n-plans embedding_model: BAAI/bge-m3 llm_model: qwen2-vl-7b-instruct parser: dpi: 200 region_split_size: 512 ocr_lang: ch retriever: top_k_image: 3 top_k_text: 5 top_k_struct: 5 fusion_weights: [0.3, 0.4, 0.3] compliance: rules_path: config/rules.json enable_strict_mode: true4.3 视觉解析模块这里模拟的是从 PDF 图纸中提取图像并进行构件检测的流程。# src/visual_parser.py import fitz # PyMuPDF import json from PIL import Image import io class VisualParser: def __init__(self, det_model, ocr_engine): self.det_model det_model # 构件检测模型 self.ocr_engine ocr_engine # OCR引擎 def pdf_to_images(self, pdf_path, dpi200): 将PDF图纸栅格化为高分辨率图片 doc fitz.open(pdf_path) images [] for page in doc: mat fitz.Matrix(dpi / 72, dpi / 72) pix page.get_pixmap(matrixmat) img Image.open(io.BytesIO(pix.tobytes(png))).convert(RGB) images.append(img) return images def detect_elements(self, image): 检测图纸中的构件返回结构化信息 results self.det_model.predict(image, conf0.35) elements [] for r in results: for box in r.boxes: x1, y1, x2, y2 box.xyxy[0].tolist() cls self.det_model.names[int(box.cls[0])] conf float(box.conf[0]) elements.append({ type: cls, bbox: [x1, y1, x2, y2], confidence: conf }) return elements def extract_annotations(self, image): 提取图纸中的尺寸与文字标注 outputs self.ocr_engine.recognize(image) annotations [] for item in outputs: annotations.append({ text: item.text, bbox: item.position }) return annotations def parse(self, pdf_path): 完整解析流程 images self.pdf_to_images(pdf_path) parsed_pages [] for idx, img in enumerate(images): elements self.detect_elements(img) annotations self.extract_annotations(img) parsed_pages.append({ page_id: idx, image: img, elements: elements, annotations: annotations }) return parsed_pages解析完成后每页图纸都有了三个维度的信息原始图像、构件列表、标注列表。4.4 结构化索引与混合检索接下来把解析结果转成可检索的索引并实现混合检索。# src/hybrid_retriever.py import numpy as np from typing import List, Dict class HybridRetriever: def __init__(self, img_embedder, text_embedder): self.img_embedder img_embedder self.text_embedder text_embedder self.image_index [] self.text_index [] self.struct_index [] self.metadata [] def add_plan(self, parsed_pages, regulations): 将解析后的图纸和规范文本加入索引 for page in parsed_pages: # 对每个区域切块这里简化处理取整页为一块 img page[image] img_vec self.img_embedder.encode(img) self.image_index.append(img_vec) self.struct_index.append(page[elements]) self.metadata.append({page_id: page[page_id]}) # 规范文本按条切分后索引 for reg_text in regulations: vec self.text_embedder.encode(reg_text) self.text_index.append({text: reg_text, vector: vec}) def retrieve(self, query: str, top_k: int 5) - Dict: 多路检索并融合排序 q_vec self.text_embedder.encode(query) # 图像相似度 img_scores [] for vec in self.image_index: score self._cosine(q_vec, vec) img_scores.append(score) # 文本相似度 text_scores [] for item in self.text_index: score self._cosine(q_vec, item[vector]) text_scores.append({text: item[text], score: score}) # 结构化信息通过关键词与类型过滤增强 struct_scores [] for idx, elements in enumerate(self.struct_index): score self._keyword_match(query, elements) struct_scores.append({page_id: idx, score: score}) # 此处返回三路结果后续在融合层加权合并 return { image_results: img_scores, text_results: text_scores, struct_results: struct_scores } staticmethod def _cosine(a, b): return float(np.dot(a, b) / (np.linalg.norm(a) * np.linalg.norm(b) 1e-8)) staticmethod def _keyword_match(query, elements): 简单实现根据构件类型与查询关键词的重合度打分 q_keywords set(query.lower().split()) score 0.0 for elem in elements: e_type elem.get(type, ).lower() for kw in q_keywords: if kw in e_type: score 1.0 return score这个混合检索模块的核心思路是用多路召回弥补单一模态的不足。文本查询向量先同时检索图像索引和文本索引再配合结构化关键词过滤从三个粒度上找到候选信息。4.5 多模态融合生成检索完成后关键一步是把“图、文、结构”组合进 Prompt交给多模态大模型生成回答。# src/multimodal_fusion.py class MultimodalFusion: def __init__(self, llm_model): self.llm llm_model def build_prompt(self, query: str, image_results, text_results, struct_results): 构建融合上下文的Prompt image_blocks [] # 将召回的图纸区域转为图像消息 for page_id, score in image_results[:3]: image_blocks.append({ type: image, data: fplan_page_{page_id}, score: score }) text_blocks for item in text_results[:5]: text_blocks f[规范条文] {item[text]}\n struct_blocks for item in struct_results[:3]: struct_blocks f[图纸结构] {item}\n prompt f 你是一位资深的民用建筑设计合规审查专家。 请根据以下材料回答用户问题。 【图纸视觉信息】 {image_blocks} 【图纸结构化信息】 {struct_blocks} 【相关规范条文】 {text_blocks} 【用户问题】 {query} 回答要求 1. 给出明确结论符合 / 不符合 / 信息不足。 2. 引用涉及的规范条文。 3. 说明判断依据定位到图纸区域或构件。 4. 如果信息不足明确指出缺少什么。 return prompt def generate(self, prompt, images): 调用多模态LLM生成回答 messages [ { role: user, content: prompt } ] # 实际接入时将images传入LLM接口 # 这里简化处理假设self.llm是已封装的多模态模型 return self.llm.chat(messagesmessages, imagesimages)这里特别强调一点Prompt 的结构化程度直接影响合规审查的质量。工程场景下模型输出必须包含“结论 依据 推理过程”否则审计人员无法复核。所以我在 Prompt 末尾显式约束了回答格式这与通用问答的 Free Style 有本质区别。4.6 合规规则引擎为了让合规判断更可靠代码中单独增加一个规则校验层把数值比较、枚举判断这类逻辑从大模型中剥离出来。# src/compliance_engine.py import json class ComplianceEngine: def __init__(self, rules_path): with open(rules_path, r, encodingutf-8) as f: self.rules json.load(f) def check(self, query_type: str, elements: list) - dict: 根据规则检查图纸结构化元素 query_type: 例如 evacuation_distance, door_swing_direction rules self.rules.get(query_type, []) violations [] for rule in rules: target rule.get(target_type) condition rule.get(condition) limit rule.get(limit) # 找到对应构件 matched [e for e in elements if e.get(type) target] for m in matched: value m.get(condition) if value is None: violations.append({ rule_id: rule.get(id), element_id: m.get(id), issue: f缺少字段: {condition}, level: error }) elif isinstance(limit, dict): if limit.get(max) and value limit[max]: violations.append({ rule_id: rule.get(id), element_id: m.get(id), issue: f{condition}{value} 超过上限 {limit[max]}, level: rule.get(level, warning) }) return { query_type: query_type, violations: violations, status: has_violation if violations else pass }配套的规则文件示例{ evacuation_distance: [ { id: R-001, target_type: 疏散门, condition: distance_to_exit, limit: {max: 30}, level: critical } ], door_swing_direction: [ { id: R-002, target_type: 疏散门, condition: swing_direction, limit: {enum: [向外, 双向]}, level: critical } ] }规则引擎的价值是让 AI 审查具备确定性。大模型负责“理解和定位”规则引擎负责“数值判断和逻辑判断”两者各司其职比单独用大模型硬判断可靠得多。4.7 串联完整 Pipeline# src/pipeline.py from visual_parser import VisualParser from hybrid_retriever import HybridRetriever from multimodal_fusion import MultimodalFusion from compliance_engine import ComplianceEngine class PlanSightRAGPipeline: def __init__(self, visual_parser, retriever, fusion, compliance): self.parser visual_parser self.retriever retriever self.fusion fusion self.compliance compliance def run(self, pdf_path, reg_texts, query, query_typeNone): # Step 1: 解析图纸 parsed_pages self.parser.parse(pdf_path) print(f[Pipeline] 图纸解析完成共 {len(parsed_pages)} 页) # Step 2: 建立索引 self.retriever.add_plan(parsed_pages, reg_texts) print([Pipeline] 索引构建完成) # Step 3: 混合检索 results self.retriever.retrieve(query) print([Pipeline] 检索完成) # Step 4: 合规规则校验可选 compliance_result None if query_type: all_elements [] for page in parsed_pages: all_elements.extend(page[elements]) compliance_result self.compliance.check(query_type, all_elements) print(f[Pipeline] 合规规则校验完成: {compliance_result[status]}) # Step 5: 多模态融合生成 prompt self.fusion.build_prompt( query, results[image_results], results[text_results], results[struct_results] ) answer self.fusion.generate(prompt, images[p[image] for p in parsed_pages]) # Step 6: 汇总输出 return { answer: answer, compliance: compliance_result, retrieved_candidates: results }这样一条 Pipeline 就能完成从“图纸进来”到“审查结论出去”的完整流程。5. 一个完整的图纸问答与合规检查案例下面模拟一个简化案例帮助你把整个流程在脑海里跑通。5.1 场景设定图纸内容某建筑首层平面图包含两个疏散门、一个安全出口、一条疏散走道。用户问题“首层两个疏散门到达安全出口的疏散距离是否满足要求”5.2 预期输出假设疏散门到安全出口的距离分别为 18 米和 35 米规范限值 30 米。系统输出【合规结论】 不符合要求。 【违规明细】 - 构件 D-102疏散门 位置A 区西侧 疏散距离35m 规范限值30m 违规类型疏散距离超限 级别严重 【涉及规范】 - 《建筑设计防火规范》GB 50016-20142018年版第 X.X 条 【复核说明】 D-101 疏散距离为 18m符合要求。D-102 超出限值 5m建议调整疏散走道布局或增设安全出口。这个输出格式的价值在于审查结论不是一句“符合”或“不符合”而是把违规点、数值依据、规范出处全部列清楚。这样才能被工程审查人员采纳而不是一个不可解释的黑盒结论。6. 常见问题与排查思路6.1 图纸解析精度不足问题现象常见原因解决思路构件识别漏检图纸分辨率不足或构件尺寸太小调高 DPI对图纸按区域切片识别标注文字识别错误倾斜、艺术字、遮挡在 OCR 前做图像校正或结合 CAD 矢量文本层构件类别不全检测模型未覆盖该构件类型收集本地图纸数据增量训练检测模型排查建议先做可视化调试把检测框画在原图上确认模型“看到了什么”。这一步能快速暴露是模型问题还是图像质量问题。6.2 检索召回了不相关内容工程图纸问答里检索不准最常见的原因是“文本语义与图形语义不一致”。用户问“门的宽度”文本索引里有规范条文“门净宽不应小于 0.8m”图像索引里有门的局部图但两者向量距离不一定近。解决方案增加查询改写把用户问题拆成“构件 属性 规范动作”如“门宽度 检查限值”。使用重排模型Reranker对召回结果二次排序。引入标签过滤先通过结构化标签定位到“门”再做向量检索。6.3 多模态大模型不理解图纸细节如果发现模型在生成阶段“看图不识图”常见原因有三个输入图像被压缩得太多细节丢失。图像与文本混合输入时模型注意力分配不均。模型本身尺寸太小图文对齐能力不足。建议把图纸按检测出的区域切片发送而不是整页发送对重点区域使用更高的分辨率必要时改用更大参数的多模态模型或者接入专门在文档/图纸上微调的 VLM。6.4 合规规则误报规则引擎的误报通常是因为结构化数据缺失。例如检测出了门但没有提取到门的开启方向属性引擎会报“缺少字段”。这类问题的处理原则是区分“真违规”和“审查不确定”。对缺失字段统一标记为“信息不足”不直接判违规。在报告中提示需要人工复核的区域。7. 最佳实践与工程建议7.1 从真实数据反推解析模型不要一开始就追求通用目标检测模型而是从你自己的图纸库中抽样几百张标注出高频构件和典型布局然后在 YOLO 或 RT-DETR 基础上做小规模微调。这个投入产出比非常高因为不同设计院的图纸画法差异很大通用模型的泛化往往不够用。7.2 构建领域图谱或规则知识库合规检查的本质是“规范的机器可执行化”。建议把常用规范条文整理成三层结构数值限定类如“消防车道净宽 ≥ 4m”。逻辑关系类如“防火分区面积超限时必须设置防火卷帘”。枚举允许类如“疏散门开启方向必须向外或双向”。这些规则建议单独管理不要全部塞进 Prompt。Prompt 冗余会显著影响大模型的判断稳定性和推理速度。7.3 建立审计跟踪机制工程审查结果要能追溯。每一条审查结论都应该记录输入图纸的版本号解析产生的结构化数据检索到的规范条文及其版本大模型生成的回答原文规则引擎的判定结果。这些信息汇总成审计记录后既可用于复盘模型错误也能作为责任界定的依据。7.4 注意安全与授权边界图纸数据往往涉及设计单位的核心资产。在工程落地时要注意训练和推理环境部署在私有化环境中避免图纸数据外传模型访问控制遵循最小权限原则不同角色只能访问对应项目范围的图纸任何涉及图纸修改、设计变更的自动化结论都必须设置人工确认环节。7.5 性能优化方向多模态 RAG 的瓶颈通常在“图纸解析”和“图像向量化”两个环节。工程化建议图纸解析做成离线异步任务用消息队列接收任务解析结果缓存复用图像向量化可以批量预计算查询时只计算查询文本向量大模型生成阶段开启流式输出用户的等待体验会好很多如果并发量高把视觉解析、检索、生成三个模块单独部署按需扩容。8. 总结与下一步学习路线PlanSightRAG 的核心不是某个单独的模型而是“视觉优先、结构化中间表示、多路召回、规则引擎兜底、可追溯输出”这套工程化设计。它把多模态大模型的语义理解能力与传统规则引擎的确定性优势结合起来解决了纯文本 RAG 无法处理图纸的问题。如果接下来想继续深入建议按以下路线推进掌握多模态 Embedding 模型的原理与微调方法理解图、文向量空间对齐的基本逻辑深入学习 RAG 的进阶技术包括查询改写、混合检索、重排模型、评估体系针对你自己的图纸类型搭建一套可视化标注工具逐步积累领域数据集完成一个最小闭环一张图纸、三条规则、一个问答界面先跑通再优化。如果你正在做图纸问答、文档智能审核、多模态知识库相关项目可以拿这篇文章的 Pipeline 做参考从案例中的精简版开始逐步补充你自己的构件检测模型和规范规则。等有落地数据后反馈效果会比空谈架构更有价值。上面这套方案我在实际调研中拆解过不少次每次重新梳理都会有新的发现。多模态 RAG 在工程领域的应用还处于快速演进阶段模型选型、索引策略、规则设计、评估指标都没有标准答案。如果文章里有不清楚的地方或者你在实现中遇到新的问题欢迎对照自己的项目实践再做调试很多细节确实需要在真实图纸上“磨”出来。
返回列表