2. 医疗数据获取与合规基础
医疗数据可视化工程的第一步不是画图,而是把数据合法、安全地拿到手。医疗数据来源大致分为三类:医院信息系统(HIS)、电子病历(EMR/EHR)以及公开医疗数据集。三类数据在结构、粒度、获取方式和合规约束上差异很大,理解这些差异决定了后续 Python 处理流程的设计。
三类数据来源的结构差异
医院信息系统是医院运营的主干,通常包含挂号、收费、检验(LIS)、影像(PACS)、药房等子系统。HIS 数据以业务流水为主,字段规范、时间戳密集,例如一条门诊记录可能包含患者 ID、科室编码、就诊时间、费用明细。电子病历则围绕临床叙事展开,既有结构化字段(诊断编码 ICD-10、生命体征),也有大量自由文本(主诉、病程记录、出院小结)。公开医疗数据集如 MIMIC-III/IV、UCI Heart Disease、SEER 癌症登记数据,已经过一定脱敏,适合教学与算法验证,但字段语义与真实 HIS 存在差距。
从 Python 读取角度看,HIS 导出常为 CSV 或数据库表,EMR 可能以 HL7/FHIR 消息或 XML 形式存在,公开数据集多为 CSV、JSON 或 Parquet。读取前必须先确认编码(UTF-8 或 GBK)、分隔符、缺失值标记(如 NULL、-1、空字符串),否则后续统计会被污染。
数据脱敏与隐私保护
医疗数据合规的核心是“最小必要”与“去标识化”。直接标识符包括姓名、身份证号、手机号、住院号、详细地址;准标识符包括出生日期、性别、邮编、就诊日期,它们组合后可能重新识别个体。脱敏不是简单删列,而是按用途分层处理:
- 删除:姓名、身份证、联系方式等直接标识符直接移除。
- 泛化:出生日期转为年龄段(如 1985-03-12 → 30-39 岁),邮编保留前三位。
- 哈希/加盐:患者 ID 用 SHA-256 加固定盐值替换,保证同一患者跨表可关联但不可逆。
- 日期偏移:将所有就诊日期整体平移随机天数,保留时间间隔关系,破坏绝对时间。
需要强调的是,脱敏后的数据仍可能通过罕见病、极端年龄等组合被重识别,因此对外发布前应做 k-匿名或差分隐私评估。伦理层面,使用患者数据需通过机构伦理审查(IRB),公开数据集要遵守其数据使用协议(DUA),不得尝试重新识别。
Python 读取与初步检查
下面以一份模拟的门诊脱敏数据为例,演示读取与初步检查。示例数据为合理假设,仅用于教学。
import pandas as pd
import hashlib
# 读取时显式指定编码与缺失值标记
df = pd.read_csv(
"outpatient_deid.csv",
encoding="utf-8",
na_values=["NULL", "", "-1"]
)
# 初步检查:形状、列类型、缺失率
print(df.shape)
print(df.dtypes)
print(df.isna().mean().sort_values(ascending=False).head())
# 对患者ID做加盐哈希(若尚未脱敏)
SALT = "hospital_2024"
df["pid_hash"] = df["patient_id"].apply(
lambda x: hashlib.sha256((SALT + str(x)).encode()).hexdigest()
)
df = df.drop(columns=["patient_id"])
# 日期泛化为年龄段
df["age_group"] = pd.cut(
df["age"], bins=[0, 18, 40, 65, 120],
labels=["0-17", "18-39", "40-64", "65+"]
)
print(df[["age_group", "visit_type"]].value_counts().head())
运行后应重点观察三件事:缺失率最高的字段是否属于关键临床变量;哈希后患者数是否与原始唯一 ID 数一致(验证无碰撞);年龄段分布是否符合医院实际人群结构。若某字段缺失率超过 40%,需回溯数据导出环节,而不是直接填充。
数据来源与合规处理全景
下图把三类数据来源、脱敏处理链与 Python 读取检查点放在同一视图中,帮助建立从“数据在哪”到“能否安全使用”的整体判断。
把这张图当作检查清单使用:每拿到一份新数据,先定位它属于哪类来源,再确认脱敏层级是否满足当前分析目的,最后用 Python 做形状、类型、缺失率和唯一性四项基础检查。只有这四步都通过,才进入可视化阶段。
data/raw、data/deid、data/processed 三级目录,原始数据只读,脱敏脚本单独存放并记录盐值与偏移参数,确保处理过程可审计、可复现。