6、ipex-llm(原bigdl-llm)大模型微调

ipex-llm环境配置及模型下载

QLORA是一种高效微调方法,可以将内存使用降低到足以在单个48GB GPU上微调一个拥有65B参数的模型,同时保持完整的16位微调任务性能。QLORA通过一个冻结的、4位量化的预训练语言模型将梯度反向传播到低秩适配器(Low Rank Adapters,简称LoRA)

1、安装需要的包

pip install transformers==4.34.0
pip install peft==0.5.0
pip install accelerate==0.23.0

2、QLoRA 微调

2.1 低精度加载模型
model = AutoModelForCausalLM.from_pretrained(pretrained_model_name_or_path = "meta-llama/Llama-2-7b-hf",load_in_low_bit="nf4",optimize_model=False,torch_dtype=torch.float16,modules_to_not_convert=["lm_head"])
model = model.to('xpu')

指定 load_in_low_bit=“nf4” 以应用 4 位 NormalFloat 优化。 根据 QLoRA 论文,使用 “nf4” 量化比 “int4” 能达到更优的模型效果。

2.2 准备训练模型

可以应用ipex_llm.transformers.qlora中的prepare_model_for_kbit_training对模型进行预处理,以进行训练的准备。

from ipex_llm.transformers.qlora import prepare_model_for_kbit_training
model.gradient_checkpointing_enable() #可以进一步减少内存使用但速度较慢
model = prepare_model_for_kbit_training(model)

从预处理后的模型中创建一个 PEFT 模型并配置它的参数,如下所示:

from ipex_llm.transformers.qlora import get_peft_model
from peft import LoraConfigconfig = LoraConfig(r=8, lora_alpha=32, target_modules=["q_proj", "k_proj", "v_proj"], lora_dropout=0.05, bias="none", task_type="CAUSAL_LM")
model = get_peft_model(model, config)

从ipex_llm.transformers.qlora导入与IPEX-LLM兼容的 PEFT 模型,替代原先使用 bitandbytes 库和 cuda 的from peft import prepare_model_for_kbit_training, get_peft_model用法。其使用方法和用peft库进行 QLoRA 微调方法相同。

2.3 加载数据集

加载通用数据集 english quotes 来根据英语名言来微调我们的模型。

from datasets import load_dataset
data = load_dataset("Abirate/english_quotes")
data = data.map(lambda samples: tokenizer(samples["quote"]), batched=True)
2.5加载Tokenizer

分词器可以在 LLM 训练和推理中实现分词和去分词过程。您可以使用 Huggingface Transformers API来加载 LLM 推理需要的分词器,它可以与 IPEX-LLM 加载的模型无缝配合使用。对于Llama 2,对应的tokenizer类为LlamaTokenizer。

from transformers import LlamaTokenizer
tokenizer = LlamaTokenizer.from_pretrained(pretrained_model_name_or_path="meta-llama/Llama-2-7b-chat-hf", trust_remote_code=True)
tokenizer.pad_token_id = 0
tokenizer.padding_side = "left"
2.6 训练
import transformers
trainer = transformers.Trainer(model=model,train_dataset=data["train"],args=transformers.TrainingArguments(per_device_train_batch_size=4,gradient_accumulation_steps= 1,warmup_steps=20,max_steps=200,learning_rate=2e-4,save_steps=100,fp16=True,logging_steps=20,output_dir="outputs", # 这里指定你自己的输出路径optim="adamw_hf", # 尚不支持 paged_adamw_8bit优化# gradient_checkpointing=True, # #可以进一步减少内存使用但速度较慢),data_collator=transformers.DataCollatorForLanguageModeling(tokenizer, mlm=False),
)
model.config.use_cache = False  # 消除警告,进行推理时应重新启用
result = trainer.train()

最终的 LoRA 模型权重和配置文件会保存到 o u t p u t d i r / c h e c k p o i n t − m a x s t e p s / a d a p t e r m o d e l . b i n 和 {output_dir}/checkpoint-{max_steps}/adapter_model.bin和 outputdir/checkpointmaxsteps/adaptermodel.bin{output_dir}/checkpoint-{max_steps}/adapter_config.json。

3、合并模型

微调模型后,可以将QLoRA模型权重和基本模型合并并导出为Hugging Face格式。

3.1 加载预训练模型
base_model = AutoModelForCausalLM.from_pretrained("meta-llama/Llama-2-7b-hf",torch_dtype=torch.float16,device_map={"": "cpu"},)

在合并状态下,应删除 load_in_low_bit=“nf4”,因为我们需要加载原始模型作为基本模型。

3.2 合并权重
from ipex_llm.transformers.qlora import PeftModel
adapter_path = "./outputs/checkpoint-200"
lora_model = PeftModel.from_pretrained(base_model,adapter_path,device_map={"": "cpu"},torch_dtype=torch.float16,)

我们用import PeftModel from ipex_llm.transformers.qlora替代from peft import PeftModel来导入 IPEX-LLM 兼容的 PEFT 模型。

为了验证LoRA权重和预训练模型权重有效合并,我们提取第一层权重(在 llama2模型中为attention中的queries)来对比其差异。

first_weight = base_model.model.layers[0].self_attn.q_proj.weight
first_weight_old = first_weight.clone()
lora_weight = lora_model.base_model.model.model.layers[0].self_attn.q_proj.weight
assert torch.allclose(first_weight_old, first_weight)

通过merge_and_unlaod方法可以将微调后的模型与预训练的模型进行合并,并通过assert声明来验证权重是否发生变化。

lora_model = lora_model.merge_and_unload()
lora_model.train(False)
assert not torch.allclose(first_weight_old, first_weight)

如果返回一下输出并没有报错,则说明模型合并成功。

Using pad_token, but it is not set yet.
Using pad_token, but it is not set yet.

最后,我们可以将合并的模型保存在指定的本地路径中。

output_path = ./outputs/checkpoint-200-merged
lora_model_sd = lora_model.state_dict()
deloreanized_sd = {k.replace("base_model.model.", ""): vfor k, v in lora_model_sd.items()if "lora" not in k}
base_model.save_pretrained(output_path, state_dict=deloreanized_sd)
tokenizer.save_pretrained(output_path)

4、使用微调模型进行推理

model_path = "./outputs/checkpoint-200-merged"
model = AutoModelForCausalLM.from_pretrained(pretrained_model_name_or_path = model_path,load_in_4bit=True)
model = model.to('xpu')
tokenizer = LlamaTokenizer.from_pretrained(pretrained_model_name_or_path = model_path)

可以验证微调模型在增添新的数据集训练后是否能做出富有哲理的回答。

with torch.inference_mode():input_ids = tokenizer.encode('The paradox of time and eternity is', return_tensors="pt").to('xpu')output = model.generate(input_ids, max_new_tokens=32)output = output.cpu()output_str = tokenizer.decode(output[0], skip_special_tokens=True)print(output_str)

仅替换model_path参数来使用预训练模型重复该过程,将预训练模型的答案与微调模型的答案进行比较:
预训练模型:

The paradox of time and eternity is that time is not eternal, but eternity is. nobody knows how long time is.
The paradox of time and eternity is

微调模型:

The paradox of time and eternity is that, on the one hand, we experience time as linear and progressive, and on the other hand, we experience time as cyclical. And the

可以看到微调模型的推理结果与新增数据集中有相同的词汇以及近似的文本风格。基于 IPEX-LLM 的优化,我们可以在仅仅几分钟的训练之内达到这个效果。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/809457.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

什么是队列

队列是一种特殊类型的线性表,其只允许在一端进行插入操作,而在另一端进行删除操作。具体来说,允许插入的一端称为队尾,而允许删除的一端称为队头。这种数据结构遵循“先进先出”(FIFO)的原则,即…

python实现OCR

python实现OCR 在Python中实现OCR(光学字符识别)通常需要使用第三方库,如pytesseract。以下是使用pytesseract进行OCR的基本步骤: 安装pytesseract和相关的OCR库,如tesseract-ocr。 使用pytesseract库的image_to_str…

从字符串到JSON对象:解析MinIO配置的Java实践

在日常开发中,我们经常需要从外部配置源(如参数配置、环境变量、配置文件等)获取服务所需的特定配置信息。本文将以一个具体需求为例,介绍如何使用Java处理字符串形式的MinIO存储服务配置,将其转化为JSON对象并提取关键…

ubuntu安装irtualbox注意事项

下载官网7.0版本,ubuntu22.04,安装一直出错误,查到了下面兄弟的办法,仍然不幸,最后使用apt重装,请按第二部分流程安装,安装6.1,可以用 第一部分,反正我是没搞通,7.0反复的出现相同的…

C语言读取 .ico 文件并显示数据

原来是想做光标编辑器&#xff0c;自己把绘图板的内容导出为光标格式 鼠标指针文件格式解析——Windows&#xff08;一&#xff09; (qq.com) 代码来源自 Icons | Microsoft Learn 鄙人又补充些变量可以运行微软的代码 简单代码如下 #include <stdio.h> #include &l…

神经网络模型底层原理与实现8-BERT

首先介绍什么是自监督学习&#xff1a; 普通的有监督学习是每个x对应有个y&#xff0c;x训练得到y&#xff0c;将y与y作比较&#xff0c;而自监督是没有对应y&#xff0c;直接把一部分样本x作为训练目标x&#xff0c;训练得x后和x对比 bert中如何创造x&#xff1a;以文字处理为…

4/11 QT_day5

服务器端 头文件 #ifndef WIDGET_H #define WIDGET_H#include <QWidget> #include <QTcpServer> #include <QMessageBox> #include <QTcpSocket> #include <QList> QT_BEGIN_NAMESPACE namespace Ui { class Widget; } QT_END_NAMESPACEclass …

MSTP/RSTP与STP的兼容性

原理概述 MSTP(Multiple STP)协议和RSTP(Rapid STP)协议都可以向下兼容STP&#xff08;Spanning Tree Protocol &#xff09;协议。运行MSTP/RSTP协议的交换机会根据收到的BPDU版本号信息自动判断与之相连的交换机的运行模式。如果收到的是STP BPDU&#xff0c;MSTP/RSTP交换机…

Oracle 21c 数据库迁移到DM8(达梦)数据库

一、环境准备 1、创建脚本 执行dmCreateUser.sql脚本创建GLJ用户&#xff08;注意&#xff1a;需要与需要迁移的oracle用户名一样&#xff09;&#xff0c;如&#xff0c;脚本内容如下&#xff1a; -- 开始将输出重定向到指定的日志文件 spool start /home/dmdba/dmdbms/sql/…

蓝桥杯算法题:蓝桥骑士

题目描述 小明是蓝桥王国的骑士&#xff0c;他喜欢不断突破自我。 这天蓝桥国王给他安排了 N 个对手&#xff0c;他们的战力值分别为 a_1,a_2,…,a_n&#xff0c;且按顺序阻挡在小明的前方。对于这些对手小明可以选择挑战&#xff0c;也可以选择避战。 身为高傲的骑士&#xff…

基于物联网的智能家居远程视频监控系统设计与实现

基于物联网的智能家居远程视频监控系统设计与实现 摘要&#xff1a;随着物联网技术的快速发展&#xff0c;智能家居系统已成为提升家居安全性和便利性的重要手段。本文设计并实现了一套基于物联网的智能家居远程视频监控系统&#xff0c;该系统结合了嵌入式技术、网络通信技术…

节流和防抖

节流和防抖 定义和区别: 节流和防抖的概念。 节流是一种减少函数执行频率的技术&#xff0c;它通过设定一个等待时间(delay)&#xff0c;确保函数在这段时间内只执行一次。如果在等待时间内再次触发事件&#xff0c;则不会执行函数&#xff0c;直到等待时间结束。 防抖是一种控…

【Go语言】go语言简单的变量声明和结构体使用

目录 数字类型 布尔类型 字符串类型 Rune 类型 Byte 类型 类型转换 结构体 结构体定义 结构体作为函数参数 结构体方法 1. 接收者类型 2. 方法定义 3. 值接收者 vs 指针接收者 4. 调用方式的灵活性 5. 方法集 6. 方法与继承 7. 方法声明的位置 在Go语言中&…

【Linux】sudo分权管理实战

一般sudo命令是默认安装的&#xff0c;如果你的机器里没有&#xff0c;可以使用命令 yum install sudo 来安装 [rootgaosh-64 ~]# yum install sudo 我们来看一下配置文件&#xff1a; 在上图root下面添加一行 &#xff0c;给gaosh用户加权限 [rootgaosh-64 ~]# vim /etc/su…

中移物联网 OneOS 操作系统环境搭建和工程创建

一、官网 OneOS Lite是中国移动针对物联网领域推出的轻量级操作系统&#xff0c;具有可裁剪、跨平台、低功耗、高安全等特点&#xff0c;支持ARM Cortex-A和 Cortex-M、MIPS、RISC-V等主流芯片架构&#xff0c;兼容POSIX、CMSIS等标准接口&#xff0c;支持Javascript、MicroPyt…

nvm安装详细教程(安装nvm、node、npm、cnpm、yarn及环境变量配置)

一、安装nvm 1. 下载nvm 点击 网盘下载 进行下载 2、双击下载好的 nvm-1.1.12-setup.zip 文件 3.双击 nvm-setup.exe 开始安装 4. 选择我接受&#xff0c;然后点击next 5.选择nvm安装路径&#xff0c;路径名称不要有空格&#xff0c;然后点击next 6.node.js安装路径&#…

哨兵-1A与DInSAR技术监测尼泊尔地震前后地表形变

2015年4月25号&#xff0c;尼泊尔发生里氏7.8级地震&#xff0c;超过5000人伤亡和几百万人受到影响。大量的卫星影像支持地震救援。地理学家利用卫星影像量测地震对陆地的影响。 Sentinel-1A是欧洲委员会发起的哥白尼环境监测计划中的第一颗卫星。可获取全天候的数据&#xff0…

实验6 单臂路由方式实现VLAN间路由

实验6 单臂路由方式实现VLAN间路由 一、 原理描述二、 实验目的三、 实验内容四、 实验配置五、 实验步骤1.配置IP地址2.交换机配置3.路由器配置 一、 原理描述 VLAN将一个物理的LAN在逻辑上划分为多个广播域。VLAN内的主机间可以互相通信&#xff0c;但是VLAN之间却不能互通。…

JAVAEE——网络初始

文章目录 网络发展史独立模式网络模式局域网LAN路由器的诞生 网络通信的基础IP地址端口号 认识协议OSI七层模型TCP/IP五层模型 网络发展史 独立模式 在原始的年代中电脑间想要通信需要两台电脑连接一根网线&#xff0c;但是一台电脑基本上只有一个接口。因此想要链接更多的电…

ChatGPT 写作秘籍:指导您如何利用ChatGPT撰写学术论文

ChatGPT无限次数:点击直达 ChatGPT 写作秘籍&#xff1a;指导您如何利用ChatGPT撰写学术论文 作为CSDN网站的作者&#xff0c;您可能经常面临不同类型的写作任务&#xff0c;包括学术论文的撰写。在这篇文章中&#xff0c;我们将探讨如何利用ChatGPT这一强大的文本生成工具来辅…