1、ChatGLM-6B阿里云服务器部署
整体参考
零基础,零成本,部署一个属于你的大模型
https://blog.csdn.net/qqxx6661/article/details/130311311?ops_request_misc=&request_id=&biz_id=102&utm_term=阿里云chatglm&utm_medium=distribute.pc_search_result.none-task-blog-2allsobaiduweb~default-6-130311311.142v88insert_down1,239v2insert_chatgpt&spm=1018.2226.3001.4187
shell创建虚拟环境virtualenv(-bash: virtualenv: command not found)
https://blog.csdn.net/weixin_42670402/article/details/88551804
Linux服务器后台运行python项目 + Linux命令行下终止当前程序
https://blog.csdn.net/qq_40671063/article/details/125869006
shell脚本后和前方,不要随便添加注释,否则会影响执行
2、ADGEN数据集P-tuning v2微调
参考:
1、ChatGLM-6B模型微调实战(以 ADGEN (广告生成) 数据集为例,序列长度达 2048):https://blog.csdn.net/weixin_40959890/article/details/130474267
2、ChatGLM-6B 部署与 P-Tuning 微调实战:https://mp.weixin.qq.com/s?__biz=Mzg4NDg5OTg1Mg==&mid=2247484324&idx=1&sn=c817cc028a11531be5a2669c8d81b8c7&chksm=cfb06ac7f8c7e3d152c98d759e283d9b46bfe68a8e17b5d1e4ca6d0267a4b1d19bb4694df643#rd
参数讲解(https://blog.csdn.net/sinat_14840559/article/details/131124471)
微调train脚本参数解释:
PRE_SEQ_LEN=128 # soft prompt 长度,P-tuning v2 参数
LR=1e-2 # 训练的学习率,P-tuning v2 参数
CUDA_VISIBLE_DEVICES=0 python main.py
--do_train \ # 训练
--train_file--:表示训练数据集的路径,需要是 JSON 格式的文件
--validation_file--:表示验证数据集的路径,需要是 JSON 格式的文件
--prompt_column content \ # 训练集中prompt 的key名称【可以理解为输入值的key】
--response_column summary \ # 训练集中response的key名称【可以理解为生成值的key】
--overwrite_cache \ # 是否覆盖缓存,对数据集进行tokenize,可以在对同一个数据集进行反复fine tune或debug,即不改变训练数据集时,删除此项参数,节约时间;同理,改变训练数据集时,需要保留此项参数,否则训练过程只能加载并使用旧数据缓存进行训练
--model_name_or_path THUDM/chatglm-6b \ # chatglm-6b 模型地址
--output_dir output/adgen-chatglm-6b-pt-PRE_SEQ_LEN-LR \ # 模型保存地址
--overwrite_output_dir
--max_source_length 64 \表示输入文本的最大长度,单位是 token,超过则会直接截断
--max_target_length 64 \表示输出文本的最大长度,单位是 token。输入文本和输出文本的最大长度是影响模型处理能力的重要参数,一般建议根据任务和数据集的特点选择合适的值,但不要超过 ChatGLM-6B 的序列长度限制(2048),超过则会直接截断
--per_device_train_batch_size 1 \这个参数是指每个设备上的训练批次大小,即每个 GPU / TPU 内核/ CPU 上用于训练的数据量。这个参数会影响显存的占用和训练的速度,一般来说,批次大小越大,显存占用越高,训练速度越快,但是也可能导致梯度爆炸或者欠拟合。因此,需要根据具体的任务和数据集来调整这个参数,以达到最佳的效果。
--per_device_eval_batch_size 1 \表示每个设备的评估批处理大小
--gradient_accumulation_steps 16 \这个参数是指梯度累积的次数,即在进行一次梯度更新之前,需要累积多少个小批量的梯度。这个参数可以用来解决显存不足的问题,通过减小每个小批量的大小,但是增加梯度累积的次数,来保持总的有效批量大小不变
--predict_with_generate \表示是否使用生成模式进行预测
--max_steps 3000 \表示最大训练步数,即模型在训练集上的迭代次数,可以理解为训练多少轮
--logging_steps 10 \表示记录日志的步数间隔
--save_steps 1000 \表示保存模型的步数间隔,即训练多少轮保存一次训练结果(checkpoint)
--learning_rate LR \训练的学习率,可以进行调节以取得最佳效果。用于控制模型训练的速度和效果。它的取值范围可以根据具体的任务和数据集进行调节,以取得最佳的效果。一般来说,learning_rate 越大,模型训练的速度越快,但也可能导致过拟合或不收敛。learning_rate 越小,模型训练的速度越慢,但也可能获得更好的泛化能力或收敛性(值范围在 0 到 1 之间,但也可以超过 1 或小于 0。不过,如果 learning_rate 太大或太小,都可能导致模型训练失败或效果不佳。因此,建议您从一个较小的值开始,比如 0.01 (1e-2)或 0.001 (1e-3),然后逐渐增大或减小,观察模型的表现,找到一个合适的值)
--pre_seq_len PRE_SEQ_LEN \pre_seq_len的取值范围一般是1到512,它表示自然语言指令的长度,即输入序列中的前pre_seq_len个token,具体的值需要根据自然语言指令的长度和复杂度来确定。一般来说,指令越长越复杂,pre_seq_len就需要越大,以便模型能够充分理解指令的含义。但是,pre_seq_len也不能太大,否则会占用过多的输入序列长度,导致生成内容过于单一或重复。因此,pre_seq_len的取值需要在保证指令完整性和生成多样性之间进行权衡。一种可能的方法是,根据不同的指令类型设置不同的pre_seq_len值,例如,对于简单的指令,如“生成一个笑话”,可以设置pre_seq_len为4;对于复杂的指令,如“生成一个关于环保主题的故事”,可以设置pre_seq_len为16。当然,这些值也需要根据实际的效果进行调整和优化
--quantization_bit 8 # 模型量化方式,用于降低显存需求,P-tuning v2 参数
gradient_accumulation_steps 和 per_device_train_batch_size 的关系是:它们都可以影响训练过程中的有效批次大小。有效批次大小是指每次梯度更新时使用的数据量,它等于 per_device_train_batch_size 乘以 gradient_accumulation_steps 乘以 设备数。有效批次大小会影响模型的训练速度和效果,一般来说,批次大小越大,训练速度越快,但是也可能导致梯度爆炸或者欠拟合。
train.sh 中的 PRE_SEQ_LEN 和 LR 分别是 soft prompt 长度和训练的学习率,可以进行调节以取得最佳的效果。P-Tuning-v2 方法会冻结全部的模型参数,可通过调整 quantization_bit 来被原始模型的量化等级,不加此选项则为 FP16 精度加载。
在默认配置 quantization_bit=4、per_device_train_batch_size=1、gradient_accumulation_steps=16 下,INT4 的模型参数被冻结,一次训练迭代会以 1 的批处理大小进行 16 次累加的前后向传播,等效为 16 的总批处理大小,此时最低只需 6.7G 显存。若想在同等批处理大小下提升训练效率,可在二者乘积不变的情况下,加大 per_device_train_batch_size 的值,但也会带来更多的显存消耗,请根据实际情况酌情调整。
怎么结合这两个参数使用呢?一种常见的做法是,当显存不足以支持较大的 per_device_train_batch_size 时,可以通过增加 gradient_accumulation_steps 来实现梯度累积,相当于用更多的小批次来模拟一个大批次。这样可以在不牺牲有效批次大小的情况下,节省显存和提高训练效率。但是也要注意不要设置过大的 gradient_accumulation_steps ,否则可能会导致梯度更新不及时或者内存溢出。
pre_seq_len和max_source_length的含义是差不多的,或者取值是可以参照的?
不完全是的,pre_seq_len和max_source_length的含义是不同的,但是它们之间有一定的关系。pre_seq_len是指自然语言指令的长度,而max_source_length是指整个输入序列的最大长度。一般来说,pre_seq_len应该小于或等于max_source_length,因为输入序列除了包含指令之外,还可能包含其他内容,例如上下文信息或对话历史。如果pre_seq_len大于max_source_length,那么模型就无法接收到完整的指令,也就无法正确地生成输出内容。因此,pre_seq_len和max_source_length的取值需要协调一致,以保证模型能够有效地利用输入信息。
模型推理evaluate脚本参数解释:
将 evaluate.sh 中的 CHECKPOINT 更改为训练时保存的 checkpoint 名称,运行以下指令进行模型推理和评测:
bash evaluate.sh
注 evaluate.sh 脚本如下
PRE_SEQ_LEN=128
CHECKPOINT=adgen-chatglm-6b-pt-8-1e-2
STEP=3000
CUDA_VISIBLE_DEVICES=0 python3 main.py
--do_predict
--validation_file AdvertiseGen/dev.json
--test_file AdvertiseGen/dev.json
--overwrite_cache
--prompt_column content
--response_column summary
--model_name_or_path ./output/\(CHECKPOINT/checkpoint-\)STEP
--output_dir ./output/$CHECKPOINT
--overwrite_output_dir
--max_source_length 64
--max_target_length 64
--per_device_eval_batch_size 1
--predict_with_generate
--pre_seq_len $PRE_SEQ_LEN
--quantization_bit 4
model_name_or_path:原始ChatGLM-6B模型文件路径
ptuning_checkpoint:训练完成后,生成的文件目录
注意:微调训练和评估结束后,需要修改ptuning件夹内的web_demo.sh脚本文件中相关内容,并通过此脚本文件运行部署,不可通过原web_demo.py文件启动服务,否则会出现仅可以提问,不能对话的问题。
可能出现的问题
每次单独提问,可以得到正确的答案,多个问题之后,后面的回答就可能受到之前问题的干扰,导致回答混乱,每次clear history之后再提问,可以避免这种情况。
提问需要有一个Prompt,指明问题的一个上下文信息或者分类信息。
将代码中每次推理中带的history参数置空,可以避免多个问题间干扰的问题
修改为(只能解决问答类、不依赖上下文的使用场景,对于希望从上下文中获取到辅助信息的场景,不可取):
def predict(input, chatbot, max_length, top_p, temperature, history):
chatbot.append((parse_text(input), ""))
for response, history in model.stream_chat(tokenizer, input, [], max_length=max_length, top_p=top_p,
temperature=temperature):
chatbot[-1] = (parse_text(input), parse_text(response))
yield chatbot, history
微调方法相关知识补充
(1)、P-Tunning:P-Tuning是指在预训练模型的输入层插入一些可训练的连续向量(Prompt),作为任务相关的信息,然后只对这些向量进行微调,而冻结预训练模型的其他参数。这种方法可以减少微调的参数量和数据量,提高微调的效率和泛化能力,但也可能会降低模型的交互性和生成质量。
(2)、LoRA:LoRA是指在预训练模型的每一层注入一些可训练的低秩矩阵(Low-Rank Adaptation),用于捕捉下游任务的低秩变化,然后只对这些矩阵进行微调,而冻结预训练模型的其他参数。这种方法可以减少微调的参数量和计算量,提高微调的效率和推理速度,同时保持模型的生成质量。
(3)、Finetune:Finetune是指对预训练模型的所有参数进行微调,以适应下游任务。这种方法可以充分利用预训练模型的知识,但也需要较多的计算资源和数据量,可能会导致过拟合或灾难性遗忘。
记录P-Tuning v2问题:
1、首先使用学习率为1e-2,出现了灾难性遗忘问题,具体表现为不能回答正常问题,仅能回答与微调数据集相关问题,并且语言表达能力大幅下降(不同问题,仅能生成重复性高回答)。
出现回答过长被截断问题,调整Maximum length后的回答
微调前回答结果,供对比
2、接下来,通过调整训练过程学习率为1e-4,微调结果如下
缓解(未出现)灾难性遗忘现象
3、LoRA微调
相关链接:
官方教程
https://www.bilibili.com/video/av444009850/?vd_source=a5da374da1254877975a081f85838ae3
参考代码(Lora微调基于alpaca_chinese数据集)
https://github.com/yuanzhoulvpi2017/zero_nlp
修改train.py文件内参数
修改train.sh文件内参数
LoRA Finetune
python train.py \
--train_path data/mixed_train_dataset.jsonl \
--dev_path data/mixed_dev_dataset.jsonl \
--use_lora True \
--lora_rank 8 \
--batch_size 1 \
--num_train_epochs 2 \
--save_freq 1000 \
--learning_rate 3e-5 \
--logging_steps 100 \
--max_source_seq_len 32 \
--max_target_seq_len 32 \
--save_dir checkpoints/lorafinetune \
--img_log_dir "log/fintune_log" \
--img_log_name "ChatGLM Lora Fine-Tune" \
--device cuda:0
--max_source_seq_len 400
--max_target_seq_len 300
情况下微调模型需要16GB以上显存,出现Out of Memory内存溢出错误
改为
--max_source_seq_len 64
--max_target_seq_len 64
成功运行,GPU占用率95%
训练至1000个step,显存再次爆掉,遂尝试调整为
--max_source_seq_len 32
--max_target_seq_len 32
成功运行,GPU占用率87%
训练至1000个step,显存再次爆掉,遂尝试调整为
--max_source_seq_len 16
--max_target_seq_len 16
成功运行,GPU占用率72%->83%
训练至1000个step,显存再次爆掉
不再尝试
同时参考以下文章
个人大模型 #02 单卡微调ChatGLM P-tuning + LoRA - 原石人类的文章 - 知乎
https://zhuanlan.zhihu.com/p/632054302
转为仅使用p-tuning微调方式
4、p-tuning微调
相关链接:
官方教程
https://www.bilibili.com/video/av444009850/?vd_source=a5da374da1254877975a081f85838ae3
参考代码(Lora微调基于alpaca_chinese数据集)
https://github.com/yuanzhoulvpi2017/zero_nlp
训练过程
修改train.py文件内参数
修改train.sh文件内参数
P-Tuning
python train.py \
--train_path data/mixed_train_dataset.jsonl \
--dev_path data/mixed_dev_dataset.jsonl \
--use_ptuning True \
--pre_seq_len 128 \
--batch_size 1 \
--num_train_epochs 2 \
--save_freq 800 \
--learning_rate 2e-4 \
--logging_steps 100 \
--max_source_seq_len 64 \
--max_target_seq_len 64 \
--save_dir checkpoints/ptuning \
--img_log_dir "log/fintune_log" \
--img_log_name "ChatGLM P-Tuning" \
--device cuda:0
--max_source_seq_len 400
--max_target_seq_len 300
情况下微调模型需要16GB以上显存,出现Out of Memory内存溢出错误
改为
--max_source_seq_len 64
--max_target_seq_len 64
成功运行,GPU占用率93%
默认情况下为1800个step
运行至800个step时
出现磁盘空间已满错误:
ubuntu查看磁盘空间命令:
df -a -h
-a:查看所有文件系统的磁盘空间
-h:以mb或者gb的形式显示磁盘容量
尝试删除部分冗余文件,未能解决
再次尝试删除大量冗余文件,同时save_freq参数从200修改为400,运行至800个step时,再次出现相同错误,遂save_freq参数从400修改为800
(记录问题,从未调整step,担心step次数不足,模型训练欠拟合)
整体训练时间大概30min
预测过程
device = 'cuda:0'
max_new_tokens = 300
model_path = "checkpoints/model_1000" # 模型存放路径
此参数填写为微调后模型路径checkpoints/model_1600不能成功运行,填写为本地ChatGLM-6B模型路径后成功运行(存疑,到底是使用那个模型做的预测)
tokenizer = AutoTokenizer.from_pretrained(
model_path,
trust_remote_code=True
)
model = AutoModel.from_pretrained(
model_path,
trust_remote_code=True
).half().to(device)
...
隔天继续解决,发现保存报名文件缺少4个文件,遂从官方原版ChatGLM-6B模型文件复制粘贴进model_1000和model_best
成功运行,后者比前速度快1秒左右
使用项目提供的Playground进行模型效果测试
出现错误:ModuleNotFoundError: No module named ‘altair.vegalite.v4’
pip install altair==4.2.2解决
显存占用率77%
使用ip+端口方式访问失败
隔天继续解决,参考以下文章设置阿里云服务器安全组,开放所需端口(本次设置为全部开放),成功运行,显存占用率80%
https://blog.csdn.net/weixin_53632051/article/details/126473339
使用四次之后,出现后台报错情况,同时自动重新加载模型,出现内存爆掉的情况
以下为使用自己制作的同类数据进行测试结果(数据:《家有儿女》是由北京中视美星国际文化传媒有限公司、东阳正午阳光影视有限公司联合出品,由北京天地人传媒有限公司发行,由宋丹丹、高亚麟、杨紫(第一、二部)、张一山、尤浩然、丹琳(第三、四部)等主演的现代剧,李洪是制片人。)效果一般
label_page平台体验效果并不是很好,不能起到标注数据的重大作用
以下为使用非同类数据集测试的结果,达观比赛:工业知识图谱关系抽取-高端装备制造知识图谱自动化构建数据集测试结果(数据:617号汽车故障报告故障现象一辆吉利车装用MR479发动机,行驶里程为23709公里,驾驶员反映该车在行驶中无异响,但在起步和换挡过程中车身有抖动现象,并且听到离合器内部有异响。)效果很差
(1)、
(2)、
同时,因训练过程中鲜脆内较小,只能设置
--max_source_seq_len
--max_target_seq_len
两项参数为较小值(400->64),可能出现截断训练数据集长度的情况,影响模型性能和学习效果
记录结果保存实例情况如下
以下为随手记录微调过程中考虑的外因素
目前尝试的是使用最新版本的官方ChatGLM-6B模型,目前是设备问题(显存和存储空间都不足)等以后有时间再进行尝试
https://huggingface.co/yuanzhoulvpi/chatglm6b-dddd/tree/main
已经尝试,不能正常使用和运行
版权归原作者平台所有,本文仅用于学习分享,如有侵权请联系删除,谢谢
标签:6B,训练,seq,--,max,模型,len,ChatGLM,服务器 From: https://www.cnblogs.com/aresspark/p/17494745.html