import os import json # import time os.environ["NCCL_P2P_DISABLE"] = "1" import torch # import pynvml from vllm import LLM, SamplingParams import torch.distributed as dist import re torch.cuda.empty_cache() os.environ["TRANSFORMERS_OFFLINE"] = "1" os.environ["HF_DATASETS_OFFLINE"] = "1" os.environ["PYTORCH_CUDA_ALLOC_CONF"] = "expandable_segments:True" # 加载量化模型 llm = LLM(model="/home/limeng/NLP/LLM/model/Qwen2.5-14B-Instruct-GPTQ-Int8", dtype="half",gpu_memory_utilization=0.9) # 定义采样参数 sampling_params = SamplingParams(temperature=0, top_p=0.3, max_tokens = 1500) # 推理示例 medical_record = """上海****病历姓名***科别肛肠一病区4B床号45住院号D04279ID号QG12005357入院记录姓名:***性别:男年龄:59岁民族:汉族籍贯:******婚姻:已婚职业:农民供史者:患者本人现居住地址:江苏省***********入院时间:2022-03-0107:45记录时间:2022-03-0110:43主诉:排便困难1年。现病史:患者于1年前无明显诱因出现排便困难。不伴大便习惯和性状改变,无便血,无黑便,有排便困难,无大便性状改变,无腹泻,无里急后重,不伴腹痛,不伴腹胀,不伴腹部肿块,不伴恶心,不伴呕吐等不适,无肠梗阻,无肠穿孔。有远处转移,有肝转移,无肺转移,无腹膜转移,无骨转移,无锁骨上淋巴结转移,无腹股沟淋巴结转移,无腹膜后淋巴结转移,无其他转移。于2021年02月19日至“我院”行肠镜+病理检查提示:插镜至50cm处结肠,见占肠腔近一周溃疡型肿块,质脆,糜烂,易出血;乙状结肠可见一0.8cm*0.8cm大小息肉。未行新辅助放疗,2021年02月19日开始,行新辅助化疗,化疗方案为CapeOx,化疗期数为7次,间隔3天,属一线化疗方案,2021年02月19日开始,2022年03月12日结束,给予安维汀。不良反应无。2021年9月8日,给予CT引导下肝占位溶瘤病毒注射术,术后继续行XELOX+安维汀治疗1周期。2021-10-11、2021-12-3行肝HAIC术+肠系膜下动脉化疗灌注术(氟尿嘧啶+奥沙利铂),术前联合贝伐珠单抗静滴。近两次灌注化疗改为FOLFIRI方案,1.14日停用靶向药物安维汀。已行新辅助治疗后评估,2022-02-27MR增强:乙状结肠局部管壁增厚,长约3.6cm,周围脂肪间隙稍模糊,管腔狭窄,增强后轻度强化。。今为进一步治疗来我院就诊,门诊以\"乙状结肠癌;肝转移癌\"收入院。自发病以来,病人精神状态良好,体力情况良好,食欲食量良好,睡眠情况良好,体重无明显变化,小便正常。仍需治疗的其他疾病情况:有高血压,无糖尿病,有冠心病,无心肌梗塞,无支架植入,无脑卒中,有肝炎,无其他,。入院前仍在服用的治疗药物:长期服药马来酸左氨氯地平片,缬沙坦氢氯噻嗪片。既往史:既往一般健康状况良好,否认“伤寒、结核、肝炎”等传染病史及接触史,否认外伤史,否认手术史,否认腹部手术史,否认输血史、否认食物、药物过敏史,过敏原,按当地防疫部门要求预防接种,呼吸系统疾病无,心血管系统疾病无,消化系统疾病无,泌尿系统疾病无,血液系统疾病无,内分泌系统疾病无,风湿性疾病疾病无,无肿瘤患病史,,。个人史:生于******,久居江苏省***********,无血吸虫疫源接触史。粉尘及有毒化学物品接触史无。放射性物质接触史无。无吸烟史年,支/天,已戒烟年。饮酒史无。冶游史0年无。婚育史:配偶健在,子女健在,育有1子。。家族史:父亲健在,母亲健在,兄弟姐妹健在。结直肠风险评估:一级亲属有结直肠癌史,无遗传性结直肠癌,无林奇综合征,无FAP,无Gardner's综合征,无Turcot's综合征,无考登病,无家族性青年息肉病,无P-J综合征,无其他,。有,为大肠癌。无家族遗传性疾病史。体格检查T:36.0℃,P:80次/分,R:18次/分,BP:120/80mmHg,Height:170cm,Weight:70.0kg。ECOG1分,发育正常,营养良好,正常面容,表情自如,自动体位,神志清楚,精神状态良好,查体合作。全身皮肤粘膜无黄染,无皮疹、皮下出血,无皮下结节、瘢痕,毛发分布正常,皮下无水肿,无肝掌、蜘蛛痣。浅表淋巴结肿大。头颅无畸形、压痛、包块、无眼睑水肿,结膜未见异常,眼球运动未见异常,巩膜无黄染,角膜透明,双侧瞳孔等大同圆,直径约3mm,对光反射灵敏,外耳道无异常分泌物,乳突区无压痛。外鼻无畸形,鼻通气畅,鼻翼无扇动,两侧副鼻窦区无压痛。口唇无发绀,口腔粘膜未见异常。舌苔未见异常,伸舌无偏斜、震颤,齿龈未见异常,咽部粘膜未见异常,扁桃体无肿大。颈软无抵抗,气管居中,颈动脉搏动未见异常,颈静脉无怒张,肝颈静脉回流征阴性,甲状腺无肿大,无压痛、震颤、血管杂音。胸廓未见异常,胸骨无压痛,乳房正常对称。呼吸运动未见异常,肋间隙未见异常,语颤未见异常。叩诊清音,呼吸规整,双肺呼吸音清晰,双侧肺未闻及干、湿性罗音,无胸膜摩擦音。心前区无隆起,心尖搏动未见异常,心浊音界未见异常,心率80次/分,律齐,各瓣膜听诊区未闻及病理性杂音,无心包摩擦音。腹部情况详见专科情况。脊柱正常生理弯曲,四肢活动自如,无畸形、下肢静脉曲张、杵状指(趾),关节未见异常,双下肢无浮肿。四肢肌力、肌张力未见异常,双侧肱二、三头肌腱反射未见异常,双侧膝、跟腱反射未见异常,双侧Babinski征阴性。专科情况:腹部视诊,未见肠型及蠕动波,未见腹壁静脉曲张。全腹柔软无压痛无反跳痛,未扪及腹腔包块。肝脏触诊未触及,脾脏触诊未触及,移动性浊音-。肝肾区无叩击痛。Murphy氏征阴性。腹部听诊,肠鸣音未见异常,4次/分。辅助检查:肿瘤指标:(2022-03-01本院):CEA:51.11ng/ml。CA199:666.22U/ml。肠镜+病理:(2021-02-19本院)肠镜+病理:插镜至50cm处结肠,见占肠腔近一周溃疡型肿块,质脆,糜烂,易出血;乙状结肠可见一0.8cm*0.8cm大小息肉。NRAS基因突变,KRAS,PI3KA,BRAF为野生型。错配修复基因功能完整pMMR。盆腔磁共振增强(2022-02-27本院MR增强):乙状结肠局部管壁增厚,长约3.6cm,周围脂肪间隙稍模糊,管腔狭窄,增强后轻度强化。盆壁结构正常,盆腔内未见肿大淋巴结。肝脏磁共振增强(2022-02-11本院):肝脏大小形态尚可,肝内见多发大小不等结节影,T1WI低信号、T2WI高信号改变,DWI弥散明显受限,增强后环形强化,最大位于肝右叶近膈顶部,大小约50.3×56.1mm,肝脏多发转移瘤,较前2022-01-13片大致相仿。胸部CT平扫(2022-02-10本院):双肺野纹理清晰,左肺下叶前内基底段(IM230)、右肺上叶前段(IM162、IM222)、右肺中叶外侧段(IM281)见长径范围约3-4mm的实性结节影,两肺见少许条索影。气管及主要支气管通畅。纵隔居中,纵隔、肺门未见明显肿大淋巴结影。心影不大,主动脉壁见点状钙化。胸腔未见明显积液征象,双侧胸膜未见明显增厚。甲状腺左右叶见结节样稍低密度影。肝内见多发团状稍低密度影。左肝内胆管扩张。胸部见输液港。心电图(2022-02-09本院):窦性心律;长QTc间期。深静脉血栓评估:评估分数:2。级别:中危。措施:基本预防:变换体位,下床活动,间歇充气加压装置,抗血栓压力袜。营养会诊:不需要。康复会诊:不需要。最后诊断:初步诊断:1.乙状结肠癌(T3N1M1)1.乙状结肠癌(T3N1M1)2.肝转移瘤介入术后2.肝转移瘤介入术后3.高血压病(3级很高危)3.高血压病(3级很高危)***/******/***2022-03-0111:14:422022-03-0111:12:21第0页""" # 定义 Prompt # 定义文件路径 file_path = "/home/limeng/NLP/LLM/code/LLM_extraction/record_text2.txt" from tqdm import tqdm # 打开文件并读取所有行 with open(file_path, 'r', encoding='utf-8') as file: # 读取所有行并去除每行的换行符 texts = [line.strip() for line in file.readlines()] # 输出列表 for i in range(len(texts)): medical_record = texts[i] prompt = f""" 你是一个专业的医疗信息抽取助手。请从以下病历数据中严格按照#### 示例 JSON 提取字段信息,并确保: 1. **字段必须完整**,与示例 JSON 结构完全一致,不可缺失/新增/改动任何字段 2. **重点字段精确**: - 手术史需抽提所有手术名称+时间(格式:"手术名称": "时间") - 化疗方案需按"方案名": {{时间+具体用药列表}} 格式提取 - 放疗方案需按"方案描述": {{时间+次数+剂量}} 格式提取 3. **严格空值处理**: - 字符串字段填"无" - 列表/字典字段填空列表[]/空字典{{}} - 嵌套结构需保持完整(如肿瘤患病史必须含"肿瘤类型"/"肿瘤结局"字段) 4. **严格JSON格式**: - 保持与示例完全相同的缩进/标点格式 - 确保所有括号闭合,逗号正确 - 生成第一个完整JSON后立即停止,禁止解释性文字 #### 病历数据 {medical_record} #### 示例 JSON {{ "消瘦": "有", "呕吐": "有", "恶心": "有", "腹部肿块": "有", "腹胀": "有", "腹痛": "有", "里急后重": "有", "腹泻": "有", "大便形状改变": "有", "排便困难": "有", "黑便": "有", "便血": "有", "大便习惯和性状改变": "有", "肠梗阻": "有", "肠穿孔": "有", "手术史": {{ "直肠癌经腹前切除+末端回肠造口术": "2017-01-11日", "冠脉支架置入术":" 2019年", }}, "肝转移": "有", "肺转移": "有", "腹膜转移": "有", "骨转移": "有", "远处转移": "有", "锁骨上转移": "有", "腹股沟转移": "有", "腹膜后淋巴结转移": "有", "其他远处淋巴转移": "无", "化疗方案": {{ "2011-1-12行XELOX方案": {{"时间": "2011-1-12" "具体用药": [ "卡培他宾1.5g 2/日d1-14", "奥沙利铂200mg d1" ] }}, "2022-7-17、8-9行FOLFOX+西妥昔单抗方案": {{ "时间": "2022-7-17、8-9" "具体用药": [ "奥沙利铂140mg 静滴D1", "亚叶酸钙0.6g 静滴D1", "5-FU 0.4g 静滴D1", "5-FU 4.0g 化疗泵入44h", "西妥昔单抗800mg 静滴D1" ]}} }}, "放疗方案": {{ "盆腔复发灶": {{ "时间": "2023-04-20至2023-05-30", "次数": "25", "单次剂量":"2Gy", "总剂量":"50Gy" }}, "照射方法为适形调强放疗IMRT,分割方法为常规分割,疗效评估为PR": {{ "时间": "2021年11月15日开始,2021年12月24日结束", "次数": "25", "单次剂量":"2Gy", "总剂量":"" }}, }}, "仍需治疗的其他疾病情况": ["高血压", "糖尿病"], "入院前仍在服用的治疗药物": ["硝苯地平缓释片", "达格列净", "格列齐特"], "高血压史": "有", "伤寒史": "有", "结核史": "有", "病毒性肝炎史": "有", "糖尿病史": "有", "冠心病史": "有", "冠脉支架放置": "有", "脑卒中史": "有", "其他非肿瘤疾病": [ "慢性乙型病毒性肝炎", ], "肿瘤患病史": {{ "肿瘤类型": "左肺腺癌", "肿瘤结局": "治愈" }} "吸烟史": {{ "吸烟年数": "25年", "日吸烟量": "10支/天", "是否戒烟": "已戒烟15年" }}, "饮酒史": "有" "婚育史": {{ "是否已婚": "已婚", "是否已育": "已育", "已育数量": "1女" }}, "结直肠癌家族史": {{ "遗传性结直肠癌类型": "无", "亲属类型": "弟弟", "其他遗传性肿瘤": "结肠癌" }}, "体温": "36.0℃", "呼吸": "18次/分", "心率": "80次/分", "血压": "120/80mmHg", "BMI": "19.6" "直肠指诊姿势": "膝胸位", "直肠指诊是否触及肿块": "有", "直肠指诊肿块下缘到肛缘距离": "5cm", "直肠指诊肿块下缘到齿状线距离": "无", "直肠指诊肿块活动度": "尚可", "直肠指诊指套推出是否染血": "有" "贫血貌": "有", "巩膜黄染": "有", "锁骨上淋巴结肿大": "有", "腹壁静脉曲张": "有", "肠形": "有", "腹部压痛": "有", "最后诊断":"", "初步诊断":"" }} """ # 推理 outputs = llm.generate(prompt, sampling_params) print(outputs[0].outputs[0].text) model_output = outputs[0].outputs[0].text result = {} if model_output: json_str = re.search(r'```json\n(.*?)\n```', model_output, re.DOTALL) if json_str: json_str = json_str.group(1) result_json = json.loads(json_str) else: # 如果未找到 JSON 部分,直接保存原始文本 json_str = re.search(r'#### JSON 提取结果\n(.*?)\n#### JSON 提取结果', model_output, re.DOTALL) if json_str: result_json = json.loads(json_str.group(1)) else: # 如果未找到 #### JSON 提取结果 格式,尝试提取 #### JSON 输出 格式 json_str = re.search(r'#### JSON 输出\n(.*?) 请严格', model_output, re.DOTALL) if json_str: result_json = json.loads(json_str.group(1)) else: json_str = re.search(r'#### JSON 提取结果\n(.*?) 根据提', model_output, re.DOTALL) if json_str: result_json = json.loads(json_str.group(1)) else: json_str = re.search(r'#### JSON 提取结果\n(.*?) 请严格按照示例JSON', model_output, re.DOTALL) if json_str: result_json = json.loads(json_str.group(1)) else: json_str = re.search(r'#### 生成 JSON\n(.*?)\n#### 生成 请严格按照示例JSON', model_output, re.DOTALL) if json_str: result_json = json.loads(json_str.group(1)) else: json_str = re.search(r'#### JSON 输出\n(.*?) 根据提', model_output, re.DOTALL) if json_str: result_json = json.loads(json_str.group(1)) else: json_str = re.search(r'#### 生成 JSON\n(.*?) 根据提供', model_output, re.DOTALL) if json_str: result_json = json.loads(json_str.group(1)) else: json_str = re.search(r'#### 提取 JSON\n(.*?)\n#### 提取 JSON', model_output, re.DOTALL) if json_str: result_json = json.loads(json_str.group(1)) else: json_str = re.search(r'格式正确。\n(.*?) 根据提供的', model_output, re.DOTALL) if json_str: result_json = json.loads(json_str.group(1)) else: json_str = re.search(r'#### JSON\n(.*?) 请严格按照', model_output, re.DOTALL) if json_str: result_json = json.loads(json_str.group(1)) else: json_str = re.search(r'格式正确。\n(.*?) 请严格按照示例', model_output, re.DOTALL) if json_str: result_json = json.loads(json_str.group(1)) else: json_str = re.search(r'#### JSON\n(.*?) 根据提供', model_output, re.DOTALL) if json_str: result_json = json.loads(json_str.group(1)) else: json_str = re.search(r'#### JSON 输出\n(.*?)\n#### JSON 输出', model_output, re.DOTALL) if json_str: result_json = json.loads(json_str.group(1)) else: result_json = {"error": "Invalid model output format", "original_text": medical_record, "model_output": model_output} print(result_json) with open(f"/home/limeng/NLP/LLM/code/0220/result_error/long_txt{i}.json", 'w', encoding='utf-8') as f: json.dump({"text_record": medical_record, "extracted_info": result_json}, f, ensure_ascii=False, indent=4)