一、工具选择
- OCR(结构化扫描件)
- RAG(文本检索与知识库)
- 大模型(Qwen2.5)
- 规则引擎
- 报告输出
二、技术方案
- 文本抽取(OCR + EMR 文本解析)
- 规则 + RAG 混合质控
- 自动生成提示报告
三、实操示例
- 搭建本地大模型环境
- 搭建 OCR 文档解析
- 搭建 RAG 知识库
- 写质控逻辑并推送提示
四、整合成完整系统
五、总结
医生一天能写几十份病例,质控科一个月要看成千上万条。
人工巡检靠经验、靠人盯,像用放大镜找蚂蚁:累、慢、易漏。
不巡检也不行,诊断不规范、治疗方案缺关键字、体征不完整、病程间断、入院记录和出院记录不一致、用药与指南不匹配等诸多问题接踵而至。
这些问题多数不是技术难点,而是人力无法做到 24 小时、逐字段逐要素检查。
只靠人工巡检,就像守着永远不会停的传送带。
自动质控巡检的意义在此变得尤为清晰:
AI 的记忆永远不会疲惫,规则永远不会忘记,模型可以持续比对病历、影像学描述、实验室数据。
医生不必等到质控科下发整改单再返工,而是在写病历的当下就能看到问题。当医疗记录更完整、更规范,最终受益的自然是诊疗安全本身。
让机器干盯着看,还能把质控人员解放出来做更有价值的判断和培训工作。
一、工具选择
这是医院 IT 部门最关心的部分——能不能本地部署、会不会数据外泄、维护成本高不高。
答案是完全可以用国产开源工具搭起来,数据不出医院内网,成本可控。
1. OCR(结构化扫描件)
医院里总有一些历史病历是扫描件,或者手写病程记录拍照上传的。这时候需要 OCR 把图片转成可分析的文字。
这里推荐 PaddleOCR,百度开源的,医院用得最多。
特别是它的升级版 PaddleOCR-VL,专门针对文档解析优化过,支持 109 种语言,能识别表格、公式、图表这些复杂元素。
最关键的是模型只有 0.9B 参数,普通服务器都能跑,不需要买昂贵的 GPU 集群。
模型地址: https://huggingface.co/PaddlePaddle/PaddleOCR-VL

2.RAG(文本检索与知识库)
质控需要对照医院的诊疗规范、SOP 文档来判断病历是否合规。这些文档少则几十页,多则上百页,不可能每次都让 AI 把整本规范读一遍。
这时候需要 RAG技术,把规范文档切成小块,存进向量数据库,用的时候只检索相关的那几段,既省资源又精准。
向量模型:bge-m3(智源研究院出品,国产,效果好)
向量库:FAISS(Meta 开源,可以完全本地部署)
文档存储:普通 JSON 或 Markdown 文件就够用,不需要复杂数据库

3. 大模型
这是整个方案的大脑。为了让医院可落地,推荐本地部署 Qwen2.5 7B 或 14B 版本。
为什么选 Qwen2.5?
✓ 7B 版本只需要 16GB 显存就能跑起来,医院一台普通 GPU 服务器搞定
✓ 支持 128K 长文本输入,一次能读完整份病历
✓ 指令遵循能力强,特别擅长结构化输出(输出 JSON 格式的质控报告)
✓ 中文理解能力优秀,医学术语也能准确识别
模型地址: https://huggingface.co/Qwen/Qwen2.5-7B-Instruct

4. 规则引擎
不是所有问题都需要大模型出马。比如“主诉字段是否为空”、“日期是否连续”这种,用 Python 正则表达式几行代码就搞定,又快又准。
Python + regex(正则匹配)
spaCy(用于命名实体识别)
自定义词典(医院常用药品名、诊断名称)
5. 报告输出
巡检完要把结果推送给医生。可以做个简单的 Web 界面,也可以直接推企业微信机器人。
FastAPI(提供后端接口)
Vue 或 React(做前端界面,可选)
企业微信机器人(最简单的方式)
二、技术方案
为了让方案足够落地,我们把整个流程浓缩成三个可执行模块。就像做一道菜,材料备好了,分三步炒,保证不翻车。
① 文本抽取(OCR + EMR 文本解析)
病历来自 EMR 系统,多为结构化字段(姓名、床号、入院日期)+ 非结构化文本(主诉、现病史、病程记录)混合。
第一步:处理扫描件
如果是扫描件或照片,先用 PaddleOCR 转成文字。
PaddleOCR-VL 特别擅长处理表格和复杂排版,比如检验报告单、影像报告,识别准确率能到 95% 以上。
第二步:提取关键字段
用正则表达式或轻量级 LLM 把病历解析成结构化数据:主诉、现病史、既往史、体格检查、诊断、用药记录、检查检验结果。
举个例子,医生写的病程记录是一大段文字:
患者入院后持续发热,体温最高 39.2°C,予头孢曲松 2g q12h 静滴抗感染治疗。
解析后变成:
{
"症状": "持续发热",
"体温": "39.2°C",
"用药": "头孢曲松 2g q12h 静滴",
"治疗目的": "抗感染"
}
这样后续质控就有了清晰的抓手。
② 规则 + RAG 混合质控
纯规则太硬,纯大模型太“飘”。最佳实践是:先用规则快速筛,再用 AI 深度查。
第一层 规则
这一层负责抓显而易见的问题,速度快,准确率高,比如:
字段是否缺失,日期是否不连续,字段长度是否异常,是否出现禁用词(比如大概、可能这种模糊表述)、药名是否拼写错误。
第二层 AI 质控
规则筛不出来的,交给大模型深度分析。这时候 RAG 发挥作用:
1. 把医院的诊疗规范、临床路径、用药指南都切成小段,存进向量库
2. 根据病历内容,检索出相关的规范条款
3. 把病历 + 规范条款一起喂给 Qwen2.5,让它判断是否合规
例如病历写:诊断为肺炎
AI 检索到《2023 版社区获得性肺炎诊疗规范》,发现规范要求写明:病原体类型、严重程度分级、是否需要住院。
AI 会输出质控意见:
根据《2023 版社区获得性肺炎诊疗规范》,诊断需要包含病原体类型(如细菌性、病毒性)、严重程度(轻度/中度/重度)及是否需要住院治疗的判断。当前诊断不完整,建议补充。
这种提示既有依据,又有操作指导,医生一看就知道怎么改,省时省力。
③ 自动生成提示报告
巡检完毕,系统自动生成一份质控报告,推送给医生或科室负责人。
报告包含:
发现的问题(按严重程度排序)
所依据的规范条款
修改建议(具体到哪个字段、怎么补充)
示例:
【病历质控提示】
患者:张三
床号:12 床
严重问题:
入院记录缺少"既往史"字段
依据:《病历书写基本规范》第 8 条
建议:补充患者既往疾病史、手术史、过敏史
一般问题:
诊断不完整:"肺炎"应注明病原体类型
依据:《社区获得性肺炎诊疗规范(2023 版)》
建议:补充为"细菌性肺炎"或"病毒性肺炎"
三、实操示例
好,现在我们来真刀真枪搭一个。
目标是半天时间,搭一个能用的病历质控巡检系统。这个系统能自动读病历、找问题、推送提示。
我们把这个过程拆成四个步骤。
第一步 搭建本地大模型环境
任务:把 Qwen2.5 7B 跑起来
先去 HuggingFace 把模型下载到本地。如果医院内网访问不了 HuggingFace,可以用镜像站 hf-mirror.com。
# 安装依赖
pip install transformers torch accelerate
# 下载模型(约 15GB,第一次会慢一点)
huggingface-cli download Qwen/Qwen2.5-7B-Instruct --local-dir ./qwen2.5-7b
测试一下模型是否能跑:
from transformers import AutoModelForCausalLM, AutoTokenizer
model_path = "./qwen2.5-7b"
model = AutoModelForCausalLM.from_pretrained(
model_path,
torch_dtype="auto",
device_map="auto"
)
tokenizer = AutoTokenizer.from_pretrained(model_path)
prompt = "请判断以下诊断是否规范:肺炎"
messages = [
{"role": "system", "content": "你是一个医疗质控专家。"},
{"role": "user", "content": prompt}
]
text = tokenizer.apply_chat_template(messages, tokenize=False, add_generation_prompt=True)
model_inputs = tokenizer([text], return_tensors="pt").to(model.device)
generated_ids = model.generate(**model_inputs, max_new_tokens=512)
response = tokenizer.batch_decode(generated_ids, skip_special_tokens=True)[0]
print(response)
如果能输出:诊断不够完整,应注明病原体类型和严重程度"。
说明模型已经跑通了。
提示::如果显存不够,可以加上 load_in_8bit=True 参数,把模型量化到 8 位,显存占用减半。
第二步 搭建 OCR 文档解析
任务:把扫描的病历转成可分析的文字
医院里总有一些老病历是扫描件,或者手写记录拍照上传的。
我们用 PaddleOCR-VL 来处理。
# 安装 PaddleOCR
pip install paddlepaddle-gpu paddleocr
写一个简单的 OCR 脚本:
from paddleocr import PaddleOCRVL
# 初始化 OCR 模型
pipeline = PaddleOCRVL()
# 处理扫描的病历
image_path = "病历扫描件.png"
output = pipeline.predict(image_path)
# 提取文本
for res in output:
res.print() # 打印识别结果
res.save_to_json(save_path="output") # 保存为 JSON
res.save_to_markdown(save_path="output") # 保存为 Markdown
PaddleOCR-VL 不仅能识别文字,还能识别表格、公式、图表。
比如检验报告单上的数据表格,它能直接输出成结构化的 JSON 格式,省去了后续解析的麻烦。
第三步 搭建 RAG 知识库
任务:把医院的诊疗规范变成可检索的知识库
质控需要对照规范来判断病历是否合规。
我们把规范文档切成小段,存进向量库,用的时候检索相关段落。
1. 准备规范文档
把医院的诊疗规范、临床路径、用药指南等文档整理成 Markdown 或纯文本格式,用deepseek这类大模型就可以处理。比如:
# 社区获得性肺炎诊疗规范(2023 版)
## 诊断标准
1. 诊断需包含病原体类型(细菌性/病毒性/真菌性)
2. 需注明严重程度(轻度/中度/重度)
3. 需说明是否需要住院治疗
## 治疗原则
1. 轻度患者可门诊治疗
2. 中重度患者建议住院治疗
3. 抗生素使用需依据药敏结果调整
- 2.切分文档并向量化
from sentence_transformers import SentenceTransformer
import faiss
import numpy as np
# 加载向量模型(bge-m3 中文效果好)
model = SentenceTransformer('BAAI/bge-m3')
# 读取规范文档并切分
with open('肺炎诊疗规范.txt', 'r', encoding='utf-8') as f:
text = f.read()
# 按段落切分(简单起见,按换行符切)
chunks = [c.strip() for c in text.split('\n\n') if c.strip()]
# 向量化
embeddings = model.encode(chunks)
# 存入 FAISS 向量库
dimension = embeddings.shape[1]
index = faiss.IndexFlatL2(dimension)
index.add(np.array(embeddings))
# 保存向量库
faiss.write_index(index, "规范知识库.index")
# 保存原始文本(用于后续检索)
import json
with open('规范文本.json', 'w', encoding='utf-8') as f:
json.dump(chunks, f, ensure_ascii=False)
- 3.检索相关规范
病历写"诊断为肺炎"时,系统自动检索相关规范:
# 加载向量库
index = faiss.read_index("规范知识库.index")
with open('规范文本.json', 'r', encoding='utf-8') as f:
chunks = json.load(f)
# 用户查询
query = "肺炎诊断是否规范"
query_embedding = model.encode([query])
# 检索最相关的 3 段
k = 3
distances, indices = index.search(np.array(query_embedding), k)
# 输出检索结果
for i in indices[0]:
print(f"相关规范:{chunks[i]}\n")
```
把这些规范段落和病历一起喂给 Qwen2.5,它就能给出专业的质控意见了。
提示:如果规范文档很多(比如几十份),可以给每段文本打上标签(如肺炎、用药规范)。检索时先过滤标签再做向量检索,能提升精准度。
第四步 写质控逻辑并推送提示
任务:把规则引擎 + AI 判断组合起来,生成质控报告
这是最后一步,也是最关键的一步。
我们要把前三关的能力串起来,做成一个完整的质控流程。
1. 写规则引擎
先用正则表达式抓显而易见的问题:
import re
def rule_check(medical_record):
issues = []
# 检查主诉是否为空
if not medical_record.get('主诉') or len(medical_record['主诉']) < 5:
issues.append({
"级别": "严重",
"问题": "主诉缺失或过短",
"依据": "《病历书写基本规范》第 6 条",
"建议": "主诉需完整描述患者症状及持续时间"
})
# 检查日期连续性
dates = medical_record.get('病程记录日期', [])
if len(dates) >= 2:
for i in range(1, len(dates)):
gap = (dates[i] - dates[i-1]).days
if gap > 1:
issues.append({
"级别": "一般",
"问题": f"病程记录间断:{dates[i-1]} 至 {dates[i]} 无记录",
"依据": "《病历书写基本规范》第 12 条",
"建议": "每日至少记录一次病程"
})
# 检查诊断是否过于简略
diagnosis = medical_record.get('诊断', '')
if diagnosis and len(diagnosis) < 10 and '肺炎' in diagnosis:
issues.append({
"级别": "一般",
"问题": "诊断不完整",
"依据": "需进一步 AI 判断",
"建议": None
})
return issues
2.AI 深度质控
对于规则引擎标记为"需进一步判断"的问题,交给 Qwen2.5 分析:
def ai_check(medical_record, related_guidelines):
# 构建提示词
prompt = f"""
你是一个医疗质控专家。请根据以下诊疗规范,判断病历中的诊断是否规范。
诊疗规范:
{related_guidelines}
病历诊断:
{medical_record['诊断']}
请输出 JSON 格式的质控意见:
{{
"是否规范": true/false,
"问题描述": "...",
"依据条款": "...",
"修改建议": "..."
}}
"""
messages = [
{"role": "system", "content": "你是一个医疗质控专家,输出必须是标准 JSON 格式。"},
{"role": "user", "content": prompt}
]
# 调用 Qwen2.5
text = tokenizer.apply_chat_template(messages, tokenize=False, add_generation_prompt=True)
model_inputs = tokenizer([text], return_tensors="pt").to(model.device)
generated_ids = model.generate(**model_inputs, max_new_tokens=512)
response = tokenizer.batch_decode(generated_ids, skip_special_tokens=True)[0]
# 解析 JSON 输出
import json
result = json.loads(response)
return result
3.生成完整质控报告
def generate_report(medical_record):
# 第一层:规则检查
rule_issues = rule_check(medical_record)
# 第二层:AI 检查(只对需要深度判断的项)
ai_issues = []
for issue in rule_issues:
if issue['依据'] == "需进一步 AI 判断":
# 检索相关规范
query = f"{medical_record['诊断']} 诊断规范"
query_embedding = model.encode([query])
distances, indices = index.search(np.array(query_embedding), 3)
related_guidelines = "\n".join([chunks[i] for i in indices[0]])
# AI 判断
ai_result = ai_check(medical_record, related_guidelines)
if not ai_result['是否规范']:
ai_issues.append({
"级别": "一般",
"问题": ai_result['问题描述'],
"依据": ai_result['依据条款'],
"建议": ai_result['修改建议']
})
# 合并问题
all_issues = [i for i in rule_issues if i['依据'] != "需进一步 AI 判断"] + ai_issues
# 生成报告
report = f"【病历质控提示】患者:{medical_record['姓名']}(床号:{medical_record['床号']})\n\n"
# 按严重程度分类
severe = [i for i in all_issues if i['级别'] == '严重']
normal = [i for i in all_issues if i['级别'] == '一般']
if severe:
report += "严重问题(需立即修改):\n"
for idx, issue in enumerate(severe, 1):
report += f"{idx}. {issue['问题']}\n"
report += f" 依据:{issue['依据']}\n"
report += f" 建议:{issue['建议']}\n\n"
if normal:
report += "一般问题(建议完善):\n"
for idx, issue in enumerate(normal, 1):
report += f"{idx}. {issue['问题']}\n"
report += f" 依据:{issue['依据']}\n"
report += f" 建议:{issue['建议']}\n\n"
return report
- 4.推送到企业微信
最简单的方式是用企业微信机器人。
去企业微信后台创建一个群机器人,拿到 Webhook 地址,然后:
import requests
def send_to_wechat(report, webhook_url):
data = {
"msgtype": "text",
"text": {
"content": report
}
}
requests.post(webhook_url, json=data)
# 推送报告
webhook_url = "https://qyapi.weixin.qq.com/cgi-bin/webhook/send?key=YOUR_KEY"
send_to_wechat(report, webhook_url)
医生在群里就能实时收到质控提示,点开看哪里有问题,直接去改。
提示:如果想做得更精细,可以加一个定时任务,每天凌晨自动扫描前一天的所有病历,生成汇总报告推送给科室主任。
整合成完整系统
把上面四步的代码整合成一个 FastAPI 服务:
from fastapi import FastAPI, UploadFile
import uvicorn
app = FastAPI()
@app.post("/quality_check")
async def quality_check(file: UploadFile):
# 1. OCR 识别(如果是扫描件)
if file.content_type.startswith('image'):
ocr_result = pipeline.predict(file.file)
text = ocr_result[0].get_text()
else:
text = await file.read()
text = text.decode('utf-8')
# 2. 解析病历字段
medical_record = parse_medical_record(text)
# 3. 质控检查
report = generate_report(medical_record)
# 4. 推送提示
send_to_wechat(report, webhook_url)
return {"status": "success", "report": report}
if __name__ == "__main__":
uvicorn.run(app, host="0.0.0.0", port=8000)
启动服务:
python main.py
现在医生上传一份病历,系统自动:
识别文字 → 提取字段 → 规则检查 → AI 判断 → 生成报告 → 推送提示。
整个流程全自动,半分钟搞定。
总结
从管理视角看,这套系统真正的价值在于三个层面:
1. 效率革命
人工质控一个月能看 5000 份病历就顶天了,AI 一天能扫 10000 份。
更关键的是,AI 不会累、不会漏、不会因为心情不好就敷衍了事。它24 小时盯着病历库,一有新病历就立刻扫描,一发现问题就立刻提示。
2. 标准固化
以前质控标准在人脑里,每个质控员的尺度不一样,今天严明天松。现在标准固化在代码和规范库里,尺度统一,可追溯,可迭代。
新出一版诊疗规范,更新一下知识库,全院质控标准立刻同步,不需要开会培训。
3. 数据沉淀
这是最被低估的价值。
传统质控做完就完了,顶多写个月报。AI 质控每扫一份病历,就沉淀一条数据,哪个科室问题最多?哪类问题最高发?哪个医生进步最快?每月都能清楚知道。