跳转至

MedCase-Structured: A Text-to-FHIR Dataset for Benchmarking Diagnostic Reasoning in Clinically Realistic EHR Settings

会议: ICML2026
arXiv: 2605.30295
代码: https://github.com/SystemInternal/MedCase-Structured (有)
领域: 医疗NLP 关键词: FHIR、临床决策支持、术语接地、合成 EHR、诊断推理

一句话总结

作者提出一个把自由文本病例转成符合 HL7 FHIR R4 标准的"分阶段 LLM + 术语接地 + 修复循环"流水线,并据此从 MedCaseReasoning 构造出 1408 条结构化合成病例数据集 MedCase-Structured(成功率 82.5%),实验显示 GPT-5.4 / Gemini-3.1-Pro / Claude-Opus-4.6 在结构化 FHIR 输入上的诊断准确率比纯文本输入一致下降 4–23 个点。

研究背景与动机

领域现状:基于 LLM 的临床决策支持系统(CDSS)越来越多被讨论,标准评测要么用 MedQA 之类的纯文本 QA,要么用 MIMIC-IV 这类受限的真实 EHR;现代医院系统普遍以 HL7 FHIR 资源对象在不同模块之间交换患者数据。

现有痛点:现成 benchmark 与真实部署形态不匹配——(1) 纯文本病例没法测模型在结构化、互操作格式上的鲁棒性;(2) MIMIC-IV-FHIR 是离线"逆向映射",分布单一且受隐私限制;(3) Synthea 基于规则模板生成,临床多样性有限、压力测试维度不够;(4) FHIR-GPT/Infherno 之类的 text→FHIR 方法目标是"忠实重建"已有病例,而不是生成可控、可批量产出的评测样本。

核心矛盾:要做"部署对齐"的 CDSS 评测,必须有大批量、结构化、可控难度、且免隐私的合成 FHIR 病例;但直接让 LLM 写 FHIR 又会大量产出幻觉的医学编码(LOINC / RxNorm / SNOMED 编不出来就瞎编)和结构不合规的资源对象,质量不可用。

本文目标:拆成两件事——(a) 建一条能从自由文本可控生成临床真实 FHIR R4 bundle 的流水线,把幻觉编码和结构错误压住;(b) 用这条流水线把 MedCaseReasoning 转成一个公开数据集 MedCase-Structured,并比较 LLM 在"纯文本病例"与"结构化 FHIR 病例"两种输入下的诊断准确率差异。

切入角度:观察到自由生成 FHIR 的失败模式集中在两类——"幻觉/不规范的标准术语码"和"资源之间的结构/语义不一致"。前者可以靠确定性的术语库 + 嵌入检索来 ground,后者可以靠多阶段拆分 + 校验-修复循环来约束。

核心 idea:把 text→FHIR 拆成"信息抽取 → 术语接地 → FHIR 合成与校验 → 诊断屏蔽"四段,LLM 只在三个固定锚点出手(抽取、合成、语义泄漏扫描),中间用 SapBERT+FAISS 的术语库做硬性接地与三阈值的接受/替换/拒绝判定,并在合成阶段接入最多 3 轮的"校验失败 → LLM 重写"修复循环。

方法详解

整体框架

输入是一份英文自由文本病例(来自 MedCaseReasoning),输出是一个通过校验的 HL7 FHIR R4 patient bundle,可选地按"诊断屏蔽模式"剔除诊断结论以做下游评测。整条流水线包含 4 个串联阶段:

  1. Extraction:LLM #1 把自由文本抽成一份扁平的中间结构(人口学、症状、体征、生命体征、化验、用药、操作、既往史),并对每个抽出来的条目保留原文 verbatim 引用作为溯源。
  2. Terminology Grounding:用一个内部维护的术语库(聚合 OMOP + SNOMED CT / LOINC / RxNorm / CVX)对 LLM 抽出的所有编码做接地:先关键词检索,再用 SapBERT 嵌入到 FAISS 索引里做语义相似度匹配,按三档余弦阈值"接受 / 替换 / 拒绝"。
  3. FHIR Synthesis and Validation:LLM #2 把已接地的中间表示按 HL7 R4 模板组装成 FHIR 资源(Patient / Encounter / Condition / Observation / MedicationRequest / Procedure / DiagnosticReport / FamilyMemberHistory / AllergyIntolerance / Immunization),失败的校验项再回灌给 LLM 重写,至多 3 轮;后处理用规则补全缺失资源、归一化单位/日期/状态字段。
  4. Diagnosis Hiding:根据 NONE / HIDDEN / EXPLICIT / FULL 四档模式对 bundle 里的诊断结论做配置化屏蔽——NONE/HIDDEN 模式下先按编码 + 子串硬过滤,再由 LLM #3 在所有叙述字段上做语义扫描,把缩写、暗示性结论、同义说法这些"隐性泄漏"再 redact 一次。

所有 LLM 调用统一用 Claude (claude-sonnet-4-20250514)、temperature 0 以求可复现。

关键设计

  1. 术语接地用 SapBERT + FAISS + 三阈值判定:

    • 功能:把 LLM 抽到的 SNOMED CT / LOINC / RxNorm / CVX 编码硬性钉死到内部术语库的真实编码上,幻觉码当场被拒。
    • 核心思路:先按关键词检索候选,再用 SapBERT 把待修候选与术语库中所有 preferred term 的嵌入索引到 FAISS,用三档余弦相似度阈值分别决定"原码可接受 / 用最近邻替换 / 直接拒绝交给修复循环"——把"是不是合法术语"从概率匹配问题变成可调阈值的检索匹配问题。
    • 设计动机:作者明确报告 Table 2 里失败案例的最大头就是 LOINC 幻觉(183 例)+ RxNorm 幻觉(126 例)+ 药物粒度过粗(103 例),不接地完全压不住;而 SapBERT 是生物医学实体的强基线嵌入,搭 FAISS 也能保持检索时延。
  2. 三段固定锚点 + 校验-修复闭环(vs agent-style):

    • 功能:让 text→FHIR 流程可控、可调试,并把"FHIR 校验器报错"显式注入回 LLM 完成修复。
    • 核心思路:与 Infherno 之类让 LLM 动态决定何时调工具的 agent 风格不同,本文把 LLM 固定调用三次(抽取、合成、语义泄漏扫描),中间夹"确定性术语接地 + 结构/临床一致性校验 + 规则后处理";合成阶段如果校验失败,把错误清单返回给 LLM 重写,至多 3 轮,超出就把该病例标为转换失败。
    • 设计动机:固定锚点比 agent 更可调试与可复现(temperature 0 + 固定调用次序),且把"语法/术语合规"这种确定性的约束从 LLM 手里收回去交给规则与术语库,让 LLM 只负责"自然语言/结构化映射"这件它擅长的事。
  3. 四模式可配置的诊断屏蔽 + 第三段 LLM 语义泄漏扫描:

    • 功能:避免下游评测时模型直接从 bundle 里"读到诊断答案",又能按需保留患者自述、家族史等合法上下文。
    • 核心思路:按 NONE / HIDDEN / EXPLICIT / FULL 四档过滤已组装的 bundle——NONE 删全部诊断结论、HIDDEN 只删主诊断、EXPLICIT 只留患者自述的状况、FULL 全保留;前两档先用编码+子串硬过滤,然后再让 LLM #3 在所有 narrative 字段上做语义扫描,揪出缩写、隐含结论、未列入同义词表的近义说法等"硬过滤抓不到"的隐性泄漏。
    • 设计动机:CDSS 评测的可信度依赖"输入里不能藏答案";FHIR bundle 的 narrative 字段恰恰是诊断信息最容易借同义词/缩写残留的地方,单靠规则 redact 拦不住,必须再借一次 LLM 做语义层扫描。

训练策略

本文不训练模型,全程用现成 Claude 闭源 API + 现成 SapBERT 嵌入 + 现成 FAISS 索引,温度固定为 0 以保证可复现;没有微调,没有 RLHF,整套系统是"LLM + 检索 + 规则校验"的合成数据流水线。

实验关键数据

主实验

数据集构造结果——把 MedCaseReasoning 原始 14,489 条病例先按规则过滤(去掉非人类、多患者、依赖影像细节的样例),再过流水线:

数据集划分 原始总数 影像类剔除 编码错误剔除 其它剔除 最终
Train 13,092 11,568 232 28 1,263
Val 500 438 10 2 50
Test 897 777 14 11 95
合计 14,489 12,783 256 41 1,408

进入流水线的样例最终成功生成 FHIR bundle 的比例为 82.5%

LLM 诊断准确率对比——把同一批病例分别以"纯文本(MCR)"与"结构化 FHIR(MCS)"两种形态喂给同一模型,比较 zero / 1-shot / 5-shot 设置:

模型 设置 MCR (%) MCS (%) Δ
GPT-5.4 zero-shot 65.26 61.05 −4.21
GPT-5.4 1-shot 74.74 51.58 −23.16
GPT-5.4 5-shot 74.74 53.68 −21.06
Gemini-3.1-Pro zero-shot 58.95 52.63 −6.32
Gemini-3.1-Pro 1-shot 65.26 53.68 −11.58
Gemini-3.1-Pro 5-shot 63.16 57.89 −5.28
Claude-Opus-4.6 zero-shot 68.42 53.63 −14.79
Claude-Opus-4.6 1-shot 69.47 54.74 −14.73
Claude-Opus-4.6 5-shot 66.32 58.95 −7.37

三家模型在所有 shot 设置下都是"结构化 FHIR 输入显著差于纯文本",最猛的一档(GPT-5.4 + 1-shot)掉了 23 个点。

失败模式分析(替代消融)

本文没做传统意义的消融,但报告了流水线在 MedCaseReasoning 上的细粒度失败模式(数量级即变相说明哪一步最吃紧):

类别 失败类型 数量 举例
术语错误 LOINC 幻觉 183 "septic workup"、"pharmacological challenge test"
术语错误 RxNorm 幻觉 126 修复后又幻觉成无效码
术语错误 药物粒度过粗 103 "oral antibiotics"、"topical corticosteroid paste"
术语错误 CVX 同义词缺口 12 "Moderna booster"、"fully immunized"
语义映射 描述过于具体 32 "loosening of lower teeth requiring dental implants"
语义映射 SNOMED 类别错配 33 操作码被赋给临床发现
排除 缺人口学 4 原文没年龄
排除 多患者 9 一份病例多名患者
排除 非人类 25 兽医病历

关键发现

  • 即使加了 3 轮校验-修复循环,术语幻觉(LOINC + RxNorm + 粒度过粗)依然是最大瓶颈(>410 例码级错误,远多于结构/语义错误),说明 SapBERT+FAISS 检索接地解决"瞎编一个看起来像样的码"已经有用,但解决不了"描述太宽泛根本对不上任何具体码"。
  • "结构化 FHIR 比纯文本难"的 gap 在 few-shot 上不缩反扩:GPT-5.4 加 1-shot/5-shot 时 MCR 涨到 74.74%,但 MCS 还在 51–53% 徘徊——示例无法把模型对 FHIR 资源对象的不熟悉补回来。
  • 影像类病例在 MedCaseReasoning 里占比极大(13,092 中有 11,568 被先验剔除,88%),因为本文流水线没建模 ImagingStudy/DiagnosticReport-imaging 资源;这是数据集留下的最大"未来工作面"。

亮点与洞察

  • "LLM 锚点 + 检索式术语库 + 校验修复循环"是给非自然语言结构化生成兜底的标准范式:让 LLM 只承担它擅长的"叙述→中间表示"映射,把"是不是合法码 / 资源结构合不合规"这种确定性约束交回给规则与检索,是结构化 EHR 之外(法律合同、报税单、配置文件、API schema 生成)都可以直接复用的模板。
  • 诊断屏蔽的"硬过滤+LLM 语义扫描"两段式是被低估的设计——naive 评测往往直接用编码黑名单做屏蔽,但 FHIR 的 narrative/text 字段会通过缩写、隐含结论、同义词把答案泄回去;这套两段式可以直接搬到其它"屏蔽答案做评测"的合成数据场景(法律/财报/考试题反推)。
  • "评测分布对齐部署形态"这件事的实证 ROI 很高:同一批病例只是换个表示就让 GPT-5.4 掉 20+ 点,意味着学界刷的 MedQA / MedCaseReasoning 排行榜与"模型真上 EHR 系统能不能用"几乎是两件事——这给后续 clinical LLM 的评测设计提供了硬证据。

局限与展望

  • 流水线只覆盖了 10 类 FHIR 资源(Patient / Encounter / Condition / Observation / MedicationRequest / Procedure / DiagnosticReport / FamilyMemberHistory / AllergyIntolerance / Immunization),关键的 ImagingStudy / Specimen / ServiceRequest / Goal 等没有,影像类病例(占原始数据 88%)整体被排除。
  • 没建模真正的纵向轨迹(同一患者多次就诊的时间序列),只用"日期感知的重复资源"代替,不能评测时间推理。
  • 术语接地仍是最大瓶颈:粒度过粗的描述("oral antibiotics")、英文同义词缺口("Moderna booster")这两类失败靠现有 SapBERT+FAISS 解决不了,需要更强的上下文感知校验或更宽的术语扩展。
  • 评测只用了三家闭源模型 + MedCaseReasoning 单一上游,未与 MIMIC-IV-FHIR、Synthea 直接做"同一模型在不同数据源"的对比;MCS 与 MCR 的 gap 里有多少来自"FHIR 难"、多少来自"作者的合成 bundle 引入了额外噪声",没有充分解耦。
  • 全管线用 Claude-Sonnet-4 自评(合成、屏蔽、并在评测里也是被测对象之一),存在轻度自家模型先验泄漏的可能;可加一个跨家族 LLM 用于合成、再用其它模型评测的交叉实验。

相关工作与启发

  • vs Synthea:Synthea 是规则模板生成,覆盖广、临床真实但多样性不足,且无法从一份给定的自由文本病例生成对应 FHIR;本文是 text-driven,临床复杂度可控但需要 LLM + 术语库的复杂工程。两者互补——做"分布广 / 大规模训练数据"用 Synthea,做"针对特定疑难病例做诊断推理评测"用本文方法。
  • vs FHIR-GPT / Infherno:这两条线把 text→FHIR 当成"忠实重建已有患者记录"的任务,目标是临床信息系统集成;本文把它当成"评测样本生产管道",强调可控性、诊断屏蔽、批量产出和评测对齐,定位差异显著。
  • vs FHIR-AgentBench / EHRStruct:这两个 benchmark 给出了"LLM 在 FHIR / 结构化 EHR 上能力如何"的评测,但用的是固定数据集,没法对临床复杂度、模糊性、屏蔽方式做可控扰动;MedCase-Structured 是把"数据集"升级为"可由文本驱动按需生成的样本工厂",跟这两个 benchmark 是上下游互补关系。
  • 给后续研究的启发:(a) 把 ImagingStudy 资源补上、与放射报告生成模型联动,能把数据集规模放大 5 倍以上;(b) "结构化 vs 文本" 的 gap 在 few-shot 上反而扩大,是个值得单独研究的 in-context learning 问题;(c) 这一套合成+屏蔽流水线可以直接拷贝到 OMOP-CDM、openEHR 等其它医疗数据标准上。

评分

  • 新颖性: ⭐⭐⭐⭐ "从自由文本可控生成评测用 FHIR" 这个定位是新的,关键组件(术语接地、修复循环、语义泄漏扫描)单看都不新,但拼起来解决一个真问题。
  • 实验充分度: ⭐⭐⭐ 流水线产出统计 + 失败模式分类做得细,但只测了 3 家闭源模型、未与 Synthea / MIMIC-IV-FHIR 做平行对比,缺消融。
  • 写作质量: ⭐⭐⭐⭐ 动机—瓶颈—方法—失败模式—评测的逻辑链很顺,Table 1/2/3 信息密度高,便于复述。
  • 价值: ⭐⭐⭐⭐ 1408 条样例 + 公开仓库 + 可控屏蔽模式,对做临床 LLM 评测的人是直接可用的;同时给出了"评测要对齐部署形态"的硬数据,影响面不小。