add literature data

We tried to use the GPT3.5 API to integrate the conclusion in the medical literature as external information into multiple rounds of dialogue, and based on this, we fine-tuned the instructions of LLaMA.
这个提交包含在:
DYR1
2023-04-24 10:00:47 +08:00
父节点 d732b74870
当前提交 eb7c87339b
共有 7 个文件被更改,包括 306 次插入19 次删除

149
README.md
查看文件

@@ -1,11 +1,19 @@
[**中文**](./README.md) | [**English**](./README_EN.md) [**中文**](./README.md) | [**English**](./README_EN.md)
<p align="center" width="100%"> <p align="center" width="100%">
<a href="https://github.com/SCIR-HI/Huatuo-Llama-Med-Chinese/" target="_blank"><img src="assets/logo/logo.png" alt="SCIR-HI-HuaTuo" style="width: 60%; min-width: 300px; display: block; margin: auto;"></a> <a href="https://github.com/SCIR-HI/Huatuo-Llama-Med-Chinese/" target="_blank"><img src="assets/logo/logo.png" alt="SCIR-HI-HuaTuo" style="width: 60%; min-width: 300px; display: block; margin: auto;"></a>
</p> </p>
# 华驼(HuaTuo): 基于中文医学知识的LLaMA微调模型 # 华驼(HuaTuo): 基于中文医学知识的LLaMA微调模型
### HuaTuo: Tuning LLaMA Model With Chinese Medical Instructions ### HuaTuo: Tuning LLaMA Model With Chinese Medical Instructions
[![Code License](https://img.shields.io/badge/Code%20License-Apache_2.0-green.svg)](https://github.com/SCIR-HI/Huatuo-Llama-Med-Chinese/blob/main/LICENSE) [![Code License](https://img.shields.io/badge/Code%20License-Apache_2.0-green.svg)](https://github.com/SCIR-HI/Huatuo-Llama-Med-Chinese/blob/main/LICENSE)
[![Python 3.9+](https://img.shields.io/badge/python-3.9+-blue.svg)](https://www.python.org/downloads/release/python-390/) [![Python 3.9+](https://img.shields.io/badge/python-3.9+-blue.svg)](https://www.python.org/downloads/release/python-390/)
@@ -13,110 +21,229 @@
基于相同的数据,我们还训练了医疗版本的ChatGLM模型: [ChatGLM-6B-Med](https://github.com/SCIR-HI/Med-ChatGLM) 基于相同的数据,我们还训练了医疗版本的ChatGLM模型: [ChatGLM-6B-Med](https://github.com/SCIR-HI/Med-ChatGLM)
此外,我们还尝试利用GPT3.5 API将医学文献中的【结论】作为外部信息融入多轮对话中,在此基础上对LLaMA进行了指令微调。目前。我们只开放针对"肝癌"单个疾病训练的模型参数。在未来,我们计划发布融入文献结论的医学对话数据集,并且会针对“肝胆胰”相关16种疾病训练模型。
我们即将发布我们研发的新模型-[扁鹊PienChueh](https://github.com/SCIR-HI/Bian-Que_Pien-Chueh),欢迎大家届时使用体验。 我们即将发布我们研发的新模型-[扁鹊PienChueh](https://github.com/SCIR-HI/Bian-Que_Pien-Chueh),欢迎大家届时使用体验。
## A Quick Start ## A Quick Start
首先安装依赖包,python环境建议3.9+ 首先安装依赖包,python环境建议3.9+
``` ```
pip install -r requirements.txt pip install -r requirements.txt
``` ```
### 模型下载 ### 模型下载
LORA权重可以通过[百度网盘](https://pan.baidu.com/s/1jih-pEr6jzEa6n2u6sUMOg?pwd=jjpf)和[HuggingFace](https://huggingface.co/thinksoso/lora-llama-med)下载
LORA权重可以通过百度网盘或Huggingface下载
- 基于医学知识库 [百度网盘](https://pan.baidu.com/s/1jih-pEr6jzEa6n2u6sUMOg?pwd=jjpf)和[HuggingFace](https://huggingface.co/thinksoso/lora-llama-med)
- 基于医学文献 [百度网盘]()
下载LORA权重并解压,解压后的格式如下 下载LORA权重并解压,解压后的格式如下
``` ```
#基于医学知识库
lora-llama-med/ lora-llama-med/
- adapter_config.json # LoRA权重配置文件
- adapter_model.bin # LoRA权重文件   - adapter_config.json   # LoRA权重配置文件
  - adapter_model.bin   # LoRA权重文件
#基于医学文献
lora-llama-med-literature/
  - adapter_config.json   # LoRA权重配置文件
  - adapter_model.bin   # LoRA权重文件
``` ```
### Infer ### Infer
我们在`./data/infer.json`中提供了一些测试用例,可以替换成其它的数据集,请注意保持格式一致 我们在`./data/infer.json`中提供了一些测试用例,可以替换成其它的数据集,请注意保持格式一致
运行infer脚本 运行infer脚本
``` ```
#基于医学知识库
bash ./scripts/infer.sh bash ./scripts/infer.sh
#基于医学文献
#单轮
bash ./scripts/infer-literature-single.sh
#多轮
bash ./scripts/infer-literature-multi.sh
``` ```
也可参考`./scripts/test.sh` 也可参考`./scripts/test.sh`
### 数据集构建 ### 数据集构建
我们采用了公开和自建的中文医学知识库,主要参考了[cMeKG](https://github.com/king-yyf/CMeKG_tools)。 我们采用了公开和自建的中文医学知识库,主要参考了[cMeKG](https://github.com/king-yyf/CMeKG_tools)。
医学知识库围绕疾病、药物、检查指标等构建,字段包括并发症,高危因素,组织学检查,临床症状,药物治疗,辅助治疗等。知识库示例如下: 医学知识库围绕疾病、药物、检查指标等构建,字段包括并发症,高危因素,组织学检查,临床症状,药物治疗,辅助治疗等。知识库示例如下:
``` ```
{"中心词": "偏头痛", "相关疾病": ["妊娠合并偏头痛", "恶寒发热"], "相关症状": ["皮肤变硬", "头部及眼后部疼痛并能听到连续不断的隆隆声", "晨起头痛加重"], "所属科室": ["中西医结合科", "内科"], "发病部位": ["头部"]} {"中心词": "偏头痛", "相关疾病": ["妊娠合并偏头痛", "恶寒发热"], "相关症状": ["皮肤变硬", "头部及眼后部疼痛并能听到连续不断的隆隆声", "晨起头痛加重"], "所属科室": ["中西医结合科", "内科"], "发病部位": ["头部"]}
``` ```
我们利用GPT3.5接口围绕医学知识库构建问答数据,设置了多种Prompt形式来充分利用知识。 我们利用GPT3.5接口围绕医学知识库构建问答数据,设置了多种Prompt形式来充分利用知识。
指令微调的训练集数据示例如下: 指令微调的训练集数据示例如下:
``` ```
"问题:一位年轻男性长期使用可卡因,突然出现胸痛、呕吐、出汗等症状,经检查发现心电图反映心肌急性损伤,请问可能患的是什么疾病?治疗方式是什么?" "问题:一位年轻男性长期使用可卡因,突然出现胸痛、呕吐、出汗等症状,经检查发现心电图反映心肌急性损伤,请问可能患的是什么疾病?治疗方式是什么?"
回答: 可能患的是心肌梗塞,需要进行维拉帕米、依普利酮、硝酸甘油、ß阻滞剂、吗啡等药物治疗,并进行溶栓治疗、低分子量肝素、钙通道阻滞剂等辅助治疗。此外需要及时停用可卡因等药物,以防止病情加重。" 回答: 可能患的是心肌梗塞,需要进行维拉帕米、依普利酮、硝酸甘油、ß阻滞剂、吗啡等药物治疗,并进行溶栓治疗、低分子量肝素、钙通道阻滞剂等辅助治疗。此外需要及时停用可卡因等药物,以防止病情加重。"
``` ```
我们提供了模型的训练数据集,共计八千余条,需要注意的是,虽然训练集的构建融入了知识,但是仍存在错误和不完善的地方,后续我们会利用更好的策略迭代更新数据集。 我们提供了模型的训练数据集,共计八千余条,需要注意的是,虽然训练集的构建融入了知识,但是仍存在错误和不完善的地方,后续我们会利用更好的策略迭代更新数据集。
指令微调数据集质量仍有限,后续将进行不断迭代,同时医学知识库和数据集构建代码还在整理中,整理完成将会发布。 指令微调数据集质量仍有限,后续将进行不断迭代,同时医学知识库和数据集构建代码还在整理中,整理完成将会发布。
此外,我们收集了2023年关于肝癌疾病的中文医学文献,利用GPT3.5接口围绕医学文献多轮问答数据。在·`./data_literature/liver_cancer.json`中我们提供了其中的1k条训练样例。
目前,训练样本的质量仍然有限,在后续我们会进一步迭代数据,会以`数据集`的形式对外进行发布。训练样本的示例如下:
<p align="center" width="100%">
<a href="https://github.com/SCIR-HI/Huatuo-Llama-Med-Chinese/" target="_blank"><img src="assets/case.png" alt="SCIR-HI-HuaTuo-literature" style="width: 100%; min-width: 300px; display: block; margin: auto;"></a>
</p>
### Finetune ### Finetune
如果想用自己的数据集微调LLaMA,请按照`./data/llama_data.json`的格式构建自己的数据集 如果想用自己的数据集微调LLaMA,请按照`./data/llama_data.json`的格式构建自己的数据集
运行finetune脚本 运行finetune脚本
``` ```
bash ./scripts/finetune.sh bash ./scripts/finetune.sh
``` ```
## 训练细节 ## 训练细节
### 计算资源需求 ### 计算资源需求
我们在一张A100-SXM-80GB显卡上进行了训练,训练总轮次10轮,耗时约2h17m。batch_size=128的情况下显存占用在40G左右。预计3090/4090显卡(24GB显存)以上显卡可以较好支持,根据显存大小来调整batch_size。 我们在一张A100-SXM-80GB显卡上进行了训练,训练总轮次10轮,耗时约2h17m。batch_size=128的情况下显存占用在40G左右。预计3090/4090显卡(24GB显存)以上显卡可以较好支持,根据显存大小来调整batch_size。
### 实验过程 ### 实验过程
超参设置和实验过程可以参考wandb的链接: 超参设置和实验过程可以参考wandb的链接:
https://wandb.ai/thinksoso/llama_med/runs/a5wgcnzt/overview?workspace=user-thinksoso https://wandb.ai/thinksoso/llama_med/runs/a5wgcnzt/overview?workspace=user-thinksoso
## 模型效果对比 ## 模型效果对比
| 测试输入 | Llama输出 | Alpaca输出 | Huatuo华驼输出|
| 测试输入 | Llama输出  | Alpaca输出 | Huatuo华驼输出|
|:------------- |:---------------| :-------------|:-------------| |:------------- |:---------------| :-------------|:-------------|
|小张最近感觉身体不适,出现心悸、气促等症状。体检发现心脏扩大、搏动减弱。|问题:小张最近感觉身体不适,出现心悸、气促等症状。体检发现心脏扩大、搏动减弱。| 最近,小张一直感觉身体不舒服,有心烦意乱、呼吸急促等症状。体格检查显示心脏增大,肌肉无力。|**小张可能患有心肌炎,建议尽快到医院进行检查和治疗。治疗方案包括药物治疗和手术治疗。**| |小张最近感觉身体不适,出现心悸、气促等症状。体检发现心脏扩大、搏动减弱。|问题:小张最近感觉身体不适,出现心悸、气促等症状。体检发现心脏扩大、搏动减弱。| 最近,小张一直感觉身体不舒服,有心烦意乱、呼吸急促等症状。体格检查显示心脏增大,肌肉无力。|**小张可能患有心肌炎,建议尽快到医院进行检查和治疗。治疗方案包括药物治疗和手术治疗。**|
|麻风病和儿童哮喘的病因是否一致?|儿童哮喘和麻风病的病因是一致,但是儿童哮喘和麻风病的病因不一致|是的,哮喘和儿童喘息有相似的原因。| **不一致,麻风病的病因是麻风杆菌感染,而儿童哮喘的病因是喂养不良、吸烟等因素。**| |麻风病和儿童哮喘的病因是否一致?|儿童哮喘和麻风病的病因是一致,但是儿童哮喘和麻风病的病因不一致|是的,哮喘和儿童喘息有相似的原因。| **不一致,麻风病的病因是麻风杆菌感染,而儿童哮喘的病因是喂养不良、吸烟等因素。**|
|一位患者出现了持续性的胀痛和黄疸,经影像学检查后确诊为肝胆管结石病,应该采取哪些治疗方案?|肝胆管结石病患者应该采取哪些治疗方案?|患者应接受手术和化疗相结合的治疗。| **针对肝胆管结石病,治疗方案包括手术治疗、药物治疗和辅助治疗等。具体治疗方案需要根据患者的具体情况而定。**| |一位患者出现了持续性的胀痛和黄疸,经影像学检查后确诊为肝胆管结石病,应该采取哪些治疗方案?|肝胆管结石病患者应该采取哪些治疗方案?|患者应接受手术和化疗相结合的治疗。| **针对肝胆管结石病,治疗方案包括手术治疗、药物治疗和辅助治疗等。具体治疗方案需要根据患者的具体情况而定。**|
## 项目参与者 ## 项目参与者
本项目由哈尔滨工业大学社会计算与信息检索研究中心健康智能组[王昊淳](https://github.com/s65b40) 、[刘驰](https://github.com/thinksoso)、[席奴瓦](https://github.com/rootnx)、[强泽文](https://github.com/1278882181)、[李子健](https://github.com/FlowolfzzZ)完成,指导教师为赵森栋副教授,秦兵教授以及刘挺教授。
本项目由哈尔滨工业大学社会计算与信息检索研究中心健康智能组[王昊淳](https://github.com/s65b40) 、[杜晏睿](https://github.com/DYR1)、[刘驰](https://github.com/thinksoso)、[白睿]()、[席奴瓦](https://github.com/rootnx)、陈雨晗、[强泽文](https://github.com/1278882181)、陈健宇、[李子健](https://github.com/FlowolfzzZ)完成,指导教师为赵森栋副教授,秦兵教授以及刘挺教授。
## 致谢 ## 致谢
本项目参考了以下开源项目,在此对相关项目和研究开发人员表示感谢。 本项目参考了以下开源项目,在此对相关项目和研究开发人员表示感谢。
- Facebook LLaMA: https://github.com/facebookresearch/llama - Facebook LLaMA: https://github.com/facebookresearch/llama
- Stanford Alpaca: https://github.com/tatsu-lab/stanford_alpaca - Stanford Alpaca: https://github.com/tatsu-lab/stanford_alpaca
- alpaca-lora by @tloen: https://github.com/tloen/alpaca-lora - alpaca-lora by @tloen: https://github.com/tloen/alpaca-lora
- CMeKG https://github.com/king-yyf/CMeKG_tools - CMeKG https://github.com/king-yyf/CMeKG_tools
- 文心一言 https://yiyan.baidu.com/welcome 本项目的logo由文心一言自动生成 - 文心一言 https://yiyan.baidu.com/welcome 本项目的logo由文心一言自动生成
## 免责声明 ## 免责声明
本项目相关资源仅供学术研究之用,严禁用于商业用途。使用涉及第三方代码的部分时,请严格遵循相应的开源协议。模型生成的内容受模型计算、随机性和量化精度损失等因素影响,本项目无法对其准确性作出保证。本项目数据集绝大部分由模型生成,即使符合某些医学事实,也不能被用作实际医学诊断的依据。对于模型输出的任何内容,本项目不承担任何法律责任,亦不对因使用相关资源和输出结果而可能产生的任何损失承担责任。 本项目相关资源仅供学术研究之用,严禁用于商业用途。使用涉及第三方代码的部分时,请严格遵循相应的开源协议。模型生成的内容受模型计算、随机性和量化精度损失等因素影响,本项目无法对其准确性作出保证。本项目数据集绝大部分由模型生成,即使符合某些医学事实,也不能被用作实际医学诊断的依据。对于模型输出的任何内容,本项目不承担任何法律责任,亦不对因使用相关资源和输出结果而可能产生的任何损失承担责任。
## Citation ## Citation
如果你使用了本项目的数据或者代码,请声明引用 如果你使用了本项目的数据或者代码,请声明引用
``` ```
@misc{wang2023huatuo, @misc{wang2023huatuo,
title={HuaTuo: Tuning LLaMA Model with Chinese Medical Knowledge},
author={Haochun Wang and Chi Liu and Nuwa Xi and Zewen Qiang and Sendong Zhao and Bing Qin and Ting Liu},       title={HuaTuo: Tuning LLaMA Model with Chinese Medical Knowledge},
year={2023},
eprint={2304.06975},       author={Haochun Wang and Chi Liu and Nuwa Xi and Zewen Qiang and Sendong Zhao and Bing Qin and Ting Liu},
archivePrefix={arXiv},
primaryClass={cs.CL}       year={2023},
      eprint={2304.06975},
      archivePrefix={arXiv},
      primaryClass={cs.CL}
} }
``` ```

二进制
assets/case.png 普通文件

二进制文件未显示。

之后

宽度:  |  高度:  |  大小: 542 KiB

文件差异因一行或多行过长而隐藏

128
infer_literature.py 普通文件
查看文件

@@ -0,0 +1,128 @@
import sys
import json
import fire
import gradio as gr
import torch
import transformers
from peft import PeftModel
from transformers import GenerationConfig, LlamaForCausalLM, LlamaTokenizer
from utils.prompter import Prompter
if torch.cuda.is_available():
device = "cuda"
def load_instruction(instruct_dir):
input_data = []
with open(instruct_dir, "r") as f:
lines = f.readlines()
for line in lines:
line = line.strip()
d = json.loads(line)
input_data.append(d)
return input_data
def main(
load_8bit: bool = False,
base_model: str = "",
# the infer data, if not exists, infer the default instructions in code
single_or_multi: str = "",
use_lora: bool = True,
lora_weights: str = "tloen/alpaca-lora-7b",
# The prompt template to use, will default to med_template.
prompt_template: str = "med_template",
):
prompter = Prompter(prompt_template)
tokenizer = LlamaTokenizer.from_pretrained(base_model)
model = LlamaForCausalLM.from_pretrained(
base_model,
load_in_8bit=load_8bit,
torch_dtype=torch.float16,
device_map="auto",
)
if use_lora:
print(f"using lora {lora_weights}")
model = PeftModel.from_pretrained(
model,
lora_weights,
torch_dtype=torch.float16,
)
# unwind broken decapoda-research config
model.config.pad_token_id = tokenizer.pad_token_id = 0 # unk
model.config.bos_token_id = 1
model.config.eos_token_id = 2
if not load_8bit:
model.half() # seems to fix bugs for some users.
model.eval()
if torch.__version__ >= "2" and sys.platform != "win32":
model = torch.compile(model)
def evaluate(
instruction,
input=None,
temperature=0.1,
top_p=0.75,
top_k=40,
num_beams=4,
max_new_tokens=256,
**kwargs,
):
prompt = prompter.generate_prompt(instruction, input)
inputs = tokenizer(prompt, return_tensors="pt")
input_ids = inputs["input_ids"].to(device)
generation_config = GenerationConfig(
temperature=temperature,
top_p=top_p,
top_k=top_k,
num_beams=num_beams,
**kwargs,
)
with torch.no_grad():
generation_output = model.generate(
input_ids=input_ids,
generation_config=generation_config,
return_dict_in_generate=True,
output_scores=True,
max_new_tokens=max_new_tokens,
)
s = generation_output.sequences[0]
output = tokenizer.decode(s)
return prompter.get_response(output)
if single_or_multi == "multi":
response=""
instruction=""
for _ in range(0,5):
inp=input("请输入:")
inp="<user>: " + inp
instruction=instruction+inp
response=evaluate(instruction)
response=response.replace('\n','')
print("Response:", response)
instruction= instruction + " <bot>: " + response
elif single_or_multi == "single":
for instruction in [
"肝癌是什么?有哪些症状和迹象?",
"肝癌是如何诊断的?有哪些检查和测试可以帮助诊断?",
"Sorafenib是一种口服的多靶点酪氨酸激酶抑制剂,它的作用机制是什么?",
"Regorafenib是一种口服的多靶点酪氨酸激酶抑制剂,它的作用机制是什么?它和Sorafenib有什么不同?",
"肝癌药物治疗的副作用有哪些?如何缓解这些副作用?",
"肝癌药物治疗的费用高昂,如何降低治疗的经济负担?",
"我想了解一下β-谷甾醇是否可作为肝癌的治疗药物",
"能介绍一下最近Hsa_circ_0008583在肝细胞癌治疗中的潜在应用的研究么?"
]:
print("instruction:",instruction)
instruction="<user>: "+instruction
print("Response:", evaluate(instruction))
if __name__ == "__main__":
fire.Fire(main)

查看文件

@@ -0,0 +1,13 @@
#!/bin/sh
# If inferring with the llama model, set 'use_lora' to 'False' and 'prompt_template' to 'ori_template'.
# If inferring with the default alpaca model, set 'use_lora' to 'True', 'lora_weights' to 'tloen/alpaca-lora-7b', and 'prompt_template' to 'alpaca'.
# If inferring with the llama-med model, download the LORA weights and set 'lora_weights' to './lora-llama-med' (or the exact directory of LORA weights) and 'prompt_template' to 'med_template'.
"""多轮交互"""
python infer_literature.py \
--base_model 'decapoda-research/llama-7b-hf' \
--lora_weights './lora-llama-literature' \
--single_or_multi 'multi' \
--use_lora True \
--prompt_template 'literature_template'

查看文件

@@ -0,0 +1,13 @@
#!/bin/sh
# If inferring with the llama model, set 'use_lora' to 'False' and 'prompt_template' to 'ori_template'.
# If inferring with the default alpaca model, set 'use_lora' to 'True', 'lora_weights' to 'tloen/alpaca-lora-7b', and 'prompt_template' to 'alpaca'.
# If inferring with the llama-med model, download the LORA weights and set 'lora_weights' to './lora-llama-med' (or the exact directory of LORA weights) and 'prompt_template' to 'med_template'.
"""单轮"""
python infer_literature.py \
--base_model 'decapoda-research/llama-7b-hf' \
--lora_weights './lora-llama-literature' \
--single_or_multi 'single' \
--use_lora True \
--prompt_template 'literature_template'

查看文件

@@ -0,0 +1,5 @@
{
"description": "Template used by Alpaca-LoRA.",
"prompt_no_input": "以下是描述任务的说明,编写适当地回复完成请求的响应。\n\n ### 说明:\n{instruction}\n\n### 回复:\n",
"response_split": "### 回复:"
}