参考链接:https://blog.csdn.net/qq_56591814/article/details/131293940https://www.bilibili.com/video/BV1WkbzeUEVD/?spm_id_from=333.880.my_history.page.click&vd_source=e01172ea292c1c605b346101d7006c61

# 一、为什么要对大模型进行微调

  通常,要对大模型进行微调,有以下一些原因:

  • 第一个原因是,因为大模型的参数量非常大,训练成本非常高,每家公司都去从头训练一个自己的大模型,这个事情的性价比非常低;

  • 第二个原因是, Prompt Engineering 的方式是一种相对来说容易上手的使用大模型的方式,但是它的缺点也非常明显。因为通常大模型的实现原理,都会对输入序列的长度有限制, Prompt Engineering 的方式会把 Prompt 搞得很长。越长的 Prompt ,大模型的推理成本越高,因为推理成本是跟 Prompt 长度的平方正向相关的。另外, Prompt 太长会因超过限制而被截断,进而导致大模型的输出质量打折口,这也是一个非常严重的问题。对于个人使用者而言,如果是解决自己日常生活、工作中的一些问题,直接用 Prompt Engineering 的方式,通常问题不大。但对于对外提供服务的企业来说,要想在自己的服务中接入大模型的能力,推理成本是不得不要考虑的一个因素,微调相对来说就是一个更优的方案。

  • 第三个原因是, Prompt Engineering 的效果达不到要求,企业又有比较好的自有数据,能够通过自有数据,更好的提升大模型在特定领域的能力。这时候微调就非常适用。

  • 第四个原因是,要在个性化的服务中使用大模型的能力,这时候针对每个用户的数据,训练一个轻量级的微调模型,就是一个不错的方案。

  • 第五个原因是,数据安全的问题。如果数据是不能传递给第三方大模型服务的,那么搭建自己的大模型就非常必要。通常这些开源的大模型都是需要用自有数据进行微调,才能够满足业务的需求,这时候也需要对大模型进行微调。

# 二、大模型微调的技术手段

  根据微调对整个预训练模型的调整程度,微调可以分为全微调和部分微调两个方法:

  • 全微调( Full Fine-tuning, FFT ): FFT 是指对整个预训练模型进行微调,包括所有的模型参数。在这种方法中,预训练模型的所有层和参数都会被更新和优化,以适应目标任务的需求。这种微调方法通常适用于任务和预训练模型之间存在较大差异的情况,或者任务需要模型具有高度灵活性和自适应能力的情况。 FFT 需要较大的计算资源和时间,但可以获得更好的性能。

  • 参数高效微调( Parameter-Efficient Fine-Tuning, PEFT ): PEFT 旨在通过最小化微调参数数量和计算复杂度,提升预训练模型在新任务上的表现,从而减轻大型预训练模型的训练负担。 PEFT 方法可以通过多种方式进行分类,比如根据其基本方法或结构进行区分 —— 是否向模型引入新的参数,还是仅微调不分现有的参数;根据微调目的进行分类 —— 是否旨在最小化内存占用或仅追求存储效率。我们首先基于基本方法 & 结构进行分类,下图展示了这个分类体系的 30PEFT 方法。接下来对 PEFT 的分类进行详细介绍。

# 2.1 Additive methods

  主要思想是通过添加额外的参数或层来扩充现有的预训练模型,并仅训练新添加的参数。到目前为止,这是参数高效微调方法中最大且广泛探索的类别。这种方法又分为:

  • Adapters :即在 Transformer 子层后引入小型全连接网络,这种方法被广泛采用。 Adapters 有多种变体,例如修改适配器的位置、剪枝以及使用重参数化来减少可训练参数的数量。
  • Soft PromptsGPT-2 旨在通过修改输入文本来控制语言模型的行为。然而,这些方法很难进行优化,且存在模型输入长度、训练示例的数量等限制,由此引入了 soft 概念。 Soft Prompts 将模型的一部分输入嵌入通过梯度下降进行微调,将在离散空间中寻找提示的问题转化为连续优化问题。 Soft Prompts 可以仅对输入层进行训练(《GPT Understands, Too》Prompt Tuning),也可以对所有层进行训练(Prefix-Tuning)。
  • others :例如 LeTS , LST(IA)^3

  尽管这些方法引入了额外的参数到网络中,但它们通过减少梯度和优化器状态的大小,减少了训练时间,提升了内存效率。此外可以对冻结的模型参数进行量化(参考论文), additive PEFT 方法能够微调更大的网络或使用更大的批次大小,这提高了在 GPU 上的训练吞吐量。此外,在分布式设置中优化较少的参数大大减少了通信量。

# 2.2 Selective methods

  最早的 selective PEFT 方法是仅微调网络的几个顶层(冻结前层),现代方法通常基于层的类型(Cross-Attention is All You Need)或内部结构,例如仅微调模型的偏置(BitFit)或仅特定的行(Efficient Fine-Tuning of BERT Models on the Edge)。

# 2.3 Reparametrization-based PEFT(重参数化)

  利用低秩表示来最小化可训练参数的数量。Aghajanyan 等人(2020)证明了在低秩子空间中可以有效地进行微调,对于更大的模型或经过更长时间预训练的模型,需要进行调整的子空间更小。最知名的基于重参数化的方法 LoRa ,它将参数矩阵进行简单的低秩分解来更新权重。最近的研究(Karimi Mahabadi 等,2021;Edalati 等,2022)还探索了 Kronecker product reparametrization 的使用,它在秩和参数数量之间取得了更有利的权衡。

   LoRA 背后有一个假设:我们现在看到的这些大语言模型,它们都是被过度参数化的。而过度参数化的大模型背后,都有一个低维的本质模型。

  大白话说:大模型参数很多,但并不是所有的参数都是发挥同样作用的;大模型中有其中一部分参数,是非常重要的,是影响大模型生成结果的关键参数,这部分关键参数就是上面提到的低维的本质模型。

   LoRA 的基本思路,包括以下几步:

  • 首先,要适配特定的下游任务,要训练一个特定的模型,将 Y=WX 变成 Y=(W+∆W)X ,这里面 ∆W 主是我们要微调得到的结果;

  • 其次,将 ∆W 进行低维分解 ∆W=AB ( ∆Wm*n 维, Am*r 维, Br*n 维, r 就是上述假设中的低维);

  • 接下来,用特定的训练数据,训练出 AB 即可得到 ∆W ,在推理的过程中直接将 ∆W 加到 W 上去,再没有额外的成本。

  • 另外,如果要用 LoRA 适配不同的场景,切换也非常方便,做简单的矩阵加法即可: (W+∆W)-∆W+∆W'

  该方法认为模型权重矩阵在特定微调后具有较低的本征秩,故基于秩分解的概念,将预训练模型的现有权重矩阵分成两个较小的矩阵。

# 2.4 Hybrid methods

  混合多种 PEFT 方法,例如, MAM Adapter 结合了 AdaptersPrompt tuningUniPELT 加入了 LoRa , CompacterKronAB 对适配器进行了重参数化以减少其参数数量;最后, S4 是一个自动化算法搜索的结果,它结合了所有的 PEFT 类别,额外参数数量增加 0.5% 的情况下最大化准确性。

# 三、使用 LLaMA-Factory 微调 Qwen2 模型

# 3.1 运行 Qwen2 模型

  首先进入下载 Qwen2 的 github 网页的运行文件。运行 Qwen2/examples/demo/web_demo.py 即可在网页端运行 Qwen2 模型。

  若本地没有大模型参数文件,则会下载 hugging face 中的参数文件。但是 hugging face 由于网络原因会导致模型下载失败。因此选择国内的 ModelScope 网站下载所需要的 Qwen2 大模型参数文件。找到对应的模型参数文件,依次点击模型文件 - 下载模型 - SDK 下载,即可获得模型参数文件的下载方式,一个示例下载的 python 程序如下所示:

#模型下载
from modelscope import snapshot_download
model_dir = snapshot_download('qwen/Qwen2-1.5B-Instruct')

  待下载完成模型文件后,更改 web_demo.py 文件的 DEFAULT_CKPT_PATH 参数为所下载模型参数文件的路径,一个示例的路径为: DEFAULT_CKPT_PATH = 'E:/python/9_LLM/2_FineTuning/4_Qwen/qwen/Qwen2-1___5B-Instruct'

  之后即可成功运行 web_demo.py ,并与所下载的大模型参数文件对应的大模型进行对话。

# 3.2 下载并运行 LLaMA-Factory

  首先进入 github LLaMA-Factory 网页,下载 LLaMA-Factory 工具箱。运行 LLaMA-Factory-main/src/webui.py 即可运行 LLaMA-Factory 的网页可视化界面。可视化界面如下所示:

# 3.3 准备数据集

  在 LLaMA-Factory-main/data 文件夹下保存了几组示例数据集的 json 文件。其中 dataset_info.json 包含了所有可用的数据集。参考 LLaMA-Factory 的说明文件,如果希望使用自定义数据集,需要在 dataset_info.json 文件中添加数据集描述,目前 LLaMA-Factory 仅支持 alpaca 格式和 sharegpt 格式的数据集。完整的数据集描述如下,具体的示例可以参考初始 dataset_info.json 文件:

"数据集名称": {
  "hf_hub_url": "Hugging Face 的数据集仓库地址(若指定,则忽略 script_url 和 file_name)",
  "ms_hub_url": "ModelScope 的数据集仓库地址(若指定,则忽略 script_url 和 file_name)",
  "script_url": "包含数据加载脚本的本地文件夹名称(若指定,则忽略 file_name)",
  "file_name": "该目录下数据集文件夹或文件的名称(若上述参数未指定,则此项必需)",
  "formatting": "数据集格式(可选,默认:alpaca,可以为 alpaca 或 sharegpt)",
  "ranking": "是否为偏好数据集(可选,默认:False)",
  "subset": "数据集子集的名称(可选,默认:None)",
  "split": "所使用的数据集切分(可选,默认:train)",
  "folder": "Hugging Face 仓库的文件夹名称(可选,默认:None)",
  "num_samples": "该数据集所使用的样本数量。(可选,默认:None)",
  "columns(可选)": {
    "prompt": "数据集代表提示词的表头名称(默认:instruction)",
    "query": "数据集代表请求的表头名称(默认:input)",
    "response": "数据集代表回答的表头名称(默认:output)",
    "history": "数据集代表历史对话的表头名称(默认:None)",
    "messages": "数据集代表消息列表的表头名称(默认:conversations)",
    "system": "数据集代表系统提示的表头名称(默认:None)",
    "tools": "数据集代表工具描述的表头名称(默认:None)",
    "images": "数据集代表图像输入的表头名称(默认:None)",
    "chosen": "数据集代表更优回答的表头名称(默认:None)",
    "rejected": "数据集代表更差回答的表头名称(默认:None)",
    "kto_tag": "数据集代表 KTO 标签的表头名称(默认:None)"
  },
  "tags(可选,用于 sharegpt 格式)": {
    "role_tag": "消息中代表发送者身份的键名(默认:from)",
    "content_tag": "消息中代表文本内容的键名(默认:value)",
    "user_tag": "消息中代表用户的 role_tag(默认:human)",
    "assistant_tag": "消息中代表助手的 role_tag(默认:gpt)",
    "observation_tag": "消息中代表工具返回结果的 role_tag(默认:observation)",
    "function_tag": "消息中代表工具调用的 role_tag(默认:function_call)",
    "system_tag": "消息中代表系统提示的 role_tag(默认:system,会覆盖 system column)"
  }
}

  添加完成数据集描述后,即可在在 LLaMA-Factory-main/data 文件夹内创建对应数据集名称的 json 文件,即可完成自定义数据集的添加。数据集的格式需要和数据集描述一致,详细的示例可以参考初始在 LLaMA-Factory-main/data 文件夹下的其他 json 数据集文件。

# 3.4 使用 LLaMA-Factory 进行大模型微调

  在准备好微调的数据集之后,即可再次运行 LLaMA-Factory-main/src/webui.py ,启动 LLaMA-Factory 的可视化界面,其中的部分参数定义如下,需要注意的是数据路径应该指定为本地计算机 LLaMA-Factory-main/data 文件夹的绝对路径:

  定义完成训练参数后即可点击 “开始” 按钮,开始模型的微调训练。模型训练完毕后,点击 Chat 选项卡,检查点路径选择训练好的大模型,即可开始与微调完成的大模型进行在线对话。点击 Export 选项卡,指定导出目录以及其他设置,点击 “开始导出”,即可导出训练完毕的大模型。至此,已经完成使用 LLaMA-Factory 进行大模型微调的全部过程。

更新于 阅读次数