模型微调(个人学习总结笔记)

什么是模型微调

在预训练好的基座模型(如LLaMA、Qwen、DeepSeek等)基础上,用特定领域或任务的数据进行二次训练,让模型更好地适配下游场景。它既能保留预训练获得的通用知识,又能显著降低训练成本,是目前企业级应用最核心的技术之一。

为什么要进行微调

|-------------|------------------------------|
| 目的 | 说明 |
| 领域适配 | 让模型学习金融、医疗、法律等行业的专业知识与术语 |
| 任务适配 | 强化模型在分类、信息抽取、代码生成等特定任务上的能力 |
| 风格与指令遵循 | 让模型输出更符合人类偏好、更遵循复杂指令 |
| 降低成本 | 用较小的微调成本,达到甚至超越超大模型在垂直任务上的效果 |
| 私有化部署 | 在企业内部数据上微调,避免数据外泄 |


二、环境准备:Windows下搭建Linux训练环境

Windows下安装Ubuntu两种方法

Windows Subsystem for Linux (WSL) 是微软官方提供的在 Windows 上运行 Linux 环境的解决方案,无需虚拟机即可获得完整的 Linux 体验。这是最推荐的方法,因为它简单、高效且与 Windows 系统深度集成。

1. 系统要求检查

在开始之前,请确保你的 Windows 系统满足以下要求:

  • Windows 10 版本 2004 及以上 (内部版本 19041 及以上)或 Windows 11
  • 系统架构为 x64 或 ARM64
  • 已启用虚拟化功能(可在 BIOS/UEFI 设置中检查)
  • 至少 4GB 可用内存(推荐 8GB 以上)
  • 至少 10GB 可用磁盘空间用于安装 Ubuntu

2. 启用 WSL 功能

WSL 功能默认是关闭的,需要手动启用。有两种方式:

方法一:使用管理员 PowerShell 一键安装(推荐)

以管理员身份打开 PowerShell 或 Windows 终端,执行以下命令。此方法会自动启用 WSL 功能并安装 Ubuntu 20.04 LTS。

bash 复制代码
# 查看可用的 Linux 发行版
wsl --list --online
安装 Ubuntu 20.04
wsl --install -d Ubuntu-20.04
或安装 Ubuntu 22.04
wsl --install -d Ubuntu-22.04

执行此命令后:

  1. 系统会自动启用 WSL 和虚拟机平台功能
  2. 下载并安装最新的 WSL 内核
  3. 设置 Ubuntu 20.04 为默认发行版
  4. 重启计算机(系统会提示)
  5. 重启后自动完成 Ubuntu 安装,并提示创建 Linux 用户名和密码

方法二:通过 Microsoft Store 安装(图形界面)

1.启用WSL和虚拟机功能

bash 复制代码
dism.exe /online/enable-feature/featurename:Microsoft-Windows-Subsystem-Linux /all/norestart
bash 复制代码
dism.exe/online/enable-feature/featurename:VirtualMachinePlatform /all/norestart

2.进入mocrisoft-store,安装ubuntu22.04

  1. 打开 Microsoft Store
  2. 搜索 "Ubuntu 20.04 LTS" 或 "Ubuntu 22.04 LTS"
  3. 点击"获取"按钮进行安装
    3.启动Ubuntu

输入

bash 复制代码
wsl -l

可以看到

输入

bash 复制代码
wsl -d Ubuntu-20.04

即可进入 Ubuntu-20.04

wsl中有一个快捷方式:

此时再输入wsl即可直接进入Ubuntu-20.04

"进入WSL后,建议先更新软件源,否则后面安装包可能会很慢"

bash 复制代码
sudo apt update && sudo apt upgrade -y

3. 初始设置与验证

安装完成后,首次启动 Ubuntu 时会进行初始设置:

  1. 系统会提示创建新的 UNIX 用户名(不能与 Windows 用户名相同)
  2. 设置密码(输入时不会显示,确保输入正确)
  3. 确认密码
  4. 系统会自动更新软件包列表

安装完成后,可以通过以下命令验证:

bash 复制代码
# 查看已安装的 WSL 发行版
wsl -l -v
进入 Ubuntu 环境
wsl
或指定发行版进入
wsl -d Ubuntu-20.04

4. 常见问题与解决方案

  • 问题: 执行 wsl --install 提示"无法解析服务器名称"
    **解决:**可能需要科学上网,或使用分步安装方法
  • 问题: 安装过程中下载速度慢
    **解决:**可以尝试更换网络环境,或使用 WSL 离线安装包
  • 问题: 启动 Ubuntu 时提示"参考的对象类型不支持尝试的操作"
    解决: 以管理员身份运行命令提示符,执行:netsh winsock reset 然后重启
  • 问题: WSL 版本选择
    建议: 推荐使用 WSL 2(性能更好),可以通过 wsl --set-default-version 2 设置

5. 后续优化配置

安装完成后,建议进行以下优化:

bash 复制代码
# 更新系统软件包
sudo apt update && sudo apt upgrade -y
安装常用开发工具
sudo apt install -y build-essential git curl wget vim
设置中国镜像源(加速下载)
sudo cp /etc/apt/sources.list /etc/apt/sources.list.backup
sudo sed -i 's/archive.ubuntu.com/mirrors.aliyun.com/g' /etc/apt/sources.list
sudo sed -i 's/security.ubuntu.com/mirrors.aliyun.com/g' /etc/apt/sources.list
sudo apt update

至此,你已经在 Windows 上成功搭建了 Linux 训练环境,可以开始进行模型微调的相关工作了。


三、安装LLaMA-Factory:一个顺手好用的微调工具

LLaMA-Factory是目前GitHub上非常活跃的微调框架,它把复杂的训练过程封装成了简单的命令行和Web界面。安装过程不难,但有几个细节值得注意。

安装系统级 distutils

bash 复制代码
sudo apt-get update
sudo apt-get install -y python3-distutils

查看驱动是否已经安装成功

bash 复制代码
nvidia-sml

安装虚拟环境

bash 复制代码
python3 -m venv finetune
source finetune/bin/activate

克隆项目代码 安装项目依赖。官方推荐的uv工具速度很快

bash 复制代码
git clone https://gitee.com/hiyouga/LLaMA-Factory.git
cd LLaMA-Factory
uv pip install -e ".[torch,metrics]" -i https://mirrors.aliyun.com/pypi/simple

验证是否安装成功,如果看到版本号,说明安装成功了

bash 复制代码
llamafactory-cli version

验证GPU是否可用,应输出 True

bash 复制代码
python -c"import torch;print{torch.cuda.is_available()}"

四、启动WebUI:图形化操作更省心

1.启动webUI界面

bash 复制代码
llamafactory-cli webui

2.云服务端口映射(在autoDL需要,可在服务器管理列表界面查询)如果用的是云服务器(比如AutoDL),需要做端口映射才能在本地浏览器访问。假设服务器SSH端口是44898,那么在本机终端执行:

bash 复制代码
### 8901是本机接口,7860是llamafactory-cli webui启动时的端口,44898是SSH的端口
ssh -L 8901:localhost:7860 -p 44898 root@connect.gda1.seetacloud.com -N
#### 即可在本机通过http://localhost:8901/访问llamafactory的web界面

之后在浏览器访问http://localhost:8901就能看到WebUI了。

WebUI的界面分为几个选项卡:训练、评估、对话、导出、API。每个选项卡都有对应的表单,填好参数点击按钮就能执行,非常适合新手探索。


五、数据准备:决定模型上限的关键环节

"数据决定模型的上限"


"人工填写、规则填充、模型回答等多个方式去得到输出数据"


"训练数据应该尽可能地模拟上线后用户会提问地问题类型语言风格还有数据这个提问地复杂程度,确保训练数据和上线后地预测数据两者地数据分布要尽量地相似,才能够使模型有更好地泛化效果"


准备数据集的3个关键:

1.数据质量比数据量重要:不管是从形式获取数据,一定要进行数据质量评估

2.数据量不要太多也不要太少:少则欠拟合,多则遗忘,边调边测

取决于任务类型和使用的基座模型 (实践中可以从1000-2000条开始,然后根据模型的效果逐渐的增减。)

  • 如果任务类型比较简单,比如说是做意图识别,那数据量不用太多。
  • 如果任务比较复杂,比如说是做知识库类的问题那取决于你的知识库的大小。
  • 如果知识库很大的话,那你的微调数据就要多一点。
  • 如果你选用的基座模型是base模型那数据量就要多一点
  • 如果是使用已经调过的Chat模型。数据量可以少一点 另外即使数据很干净,数据也不是越多越好。因为多了容易过拟合,容易造成一些灾难性遗忘(比如微调之前你问模型1+1等于多少他知道,但是微调之后他不知道了),为了避免灾难性遗忘我们可以在数据集中补充一些通用的数据集

3.注意数据的多样性:覆盖可能出现的各种问题


下载数据

复制代码
modelscope download --dataset alleyf/(数据集名称) 
--local_dir ./dataset/HUST-Student-Handbook

## 例如: modelscope download --dataset alleyf/HUST-Studet-Handbook 
--local_dir ./dataset/HUST-Student-Handbook

原始数据集的格式不符合要求怎么处理

在LLaMAFactory里面使用一个数据包含两个步骤:

第一个是在微调前提前注册这个数据

第二个是在微调时选择这个数据 (一般来说LLaMAFactory会在data文件夹中存放很多示例数据,也会在examples文件夹中放很多示例配置文件)

如何数据蒸馏,如何保障数据的多样性

要点: 输入数据和输出数据应该分开构造,便于调试 应该尽量提升提示词的产业化,提升数据的多样性

建议: 在构造输入数据时,提示词中不要有示例 在蒸馏输出数据时,提示词要加示例

(输入数据要的是多样性,示例可能会让模型过度的模拟,从而限制了想象力,输出数据要的是确定性)

github下载: https://github.com/ConardLi/easy-dataset/releases/tag/1.5.1https://github.com/ConardLi/easy-dataset/releases/tag/1.5.1


5.1数据的格式要求

LLaMA-Factory支持两种主流格式:Alpaca和ShareGPT。我一开始用了Alpaca格式,结构清晰,适合单轮指令微调。

使用数据两个步骤:一是注册到dataset_info文件,二是在配置文件中的dataset参数中指定

Alpaca格式示例(一个JSON文件,里面是一个对象数组):

bash 复制代码
[
  {
    "instruction": "请根据以下信息,生成一份产品简介。",
    "input": "产品名称:智能保温杯,容量:500ml,材质:不锈钢,特色:实时温度显示。",
    "output": "这款智能保温杯采用优质不锈钢材质,容量500ml,内置温度传感器,可实时显示水温,让您随时掌握饮水温度。"
  },
  {
    "instruction": "翻译成英文。",
    "input": "今天天气真好。",
    "output": "The weather is really nice today."
  }
]

instruction和input会拼接成模型的实际输入,output是期望的回答。

如果你的数据是多轮对话,可以使用ShareGPT格式:

SHareGPT格式示例

bash 复制代码
[
  {
    "conversations": [
      {"from": "human", "value": "你好,我想了解你们的会员服务。"},
      {"from": "gpt", "value": "您好!我们的会员服务分为三个等级..."},
      {"from": "human", "value": "那黄金会员有什么特权?"},
      {"from": "gpt", "value": "黄金会员可以享受无限次免费咨询和专属折扣。"}
    ]
  }
]

5.2 如何获取高质量数据?

  • 人工编写:针对核心场景,由业务专家撰写几百条典型问答,质量最高。

  • 规则生成:用模板填充方式快速生成大量变体(比如替换商品名称、日期等)。

  • 模型蒸馏:用更强的模型(如GPT-4)对现有文档生成问答对,再人工审核。


5.3 注册数据集------这一步容易忽略

LLaMA-Factory要求所有数据集在data/dataset_info.json中注册。打开这个文件,按以下格式添加你的数据集:

bash 复制代码
"my_dataset": {
  "file_name": "my_data.json",
  "columns": {
    "prompt": "instruction",
    "query": "input",
    "response": "output"
  }
}

如果文件在子目录,路径要写相对路径,例如"file_name": "custom/my_data.json"。

注册完成后,在训练配置的dataset参数中直接写my_dataset即可。


5.4 快速验证数据集格式

在配置文件中加上do_train: false,然后执行训练命令,程序只会加载数据并检查格式,不会真正训练。这样能快速发现问题。


六、开始训练:我的第一次微调之旅

6.1 下载基座模型

选用的是Qwen3-0.6B,因为显存有限(6GB),小模型更友好。下载模型推荐用ModelScope,速度快

bash 复制代码
cd LLaMA-Factory
pip install modelscope
modelscope download --model Qwen/Qwen3-0.6B --local_dir /mnt/d/test/models/Qwen3-0.6B

我下载到了Windows的D盘(WSL下通过/mnt/d/访问),这样模型文件不会占用WSL的虚拟磁盘空间。


6.2 编写训练配置文件

LLaMA-Factory的配置文件是YAML格式。参考examples/train_lora/llama3_lora_sft.yaml,修改成自己的参数

1.命令查询

bash 复制代码
llamafactory-cli-h

2.修改配置文件examples/train_lora/llama3_lora_sft.yaml

bash 复制代码
model_name_or_path:Qwen/Qwen3-0.6B-base
template:default
output_dir:saves/Qwen3-0.6/lora/sft

6.3 执行训练

在WSL终端执行:

bash 复制代码
cd LLaMA-Factory
USE_MODELSCOPE_HUB=1 llamafactory-cli train examples/train_lora/llama3_lora_sft.yaml

USE_MODELSCOPE_HUB=1会优先从ModelScope下载缺失的模型文件,国内网络更友好。

训练过程中,控制台会打印loss值。如果发现loss不下降,可能是学习率太高或数据有问题。


七、对话测试:看看模型学到了什么

1.准备执行chat.修改配置文件examples/inference/llama3_lora_sft.yaml

bash 复制代码
model_name_or_path:Qwen/Qwen3-0.6B-base
adapter_name_or_path:saves/Qwen3-0.6B/lora/sft
template:default

2.执行推理对话

bash 复制代码
USE_MODELSCOPE_HUB=1 llamafactory-cli chat examples/inference/llama3_lora_sft.yaml

八、合并与部署:让模型独立运行

LoRA权重不能单独使用,必须与基座模型合并。合并后得到一个完整的模型文件,方便部署。

8.1 合并LoRA权重

1.修改配置文件 examples/merge_lora/llama3_lora_sft.yaml

bash 复制代码
model_name_or_path:Qwen/Qwen3-0.6B-base
adapter_name_or_path:saves/Qwen3-0.6B/lora/sft
template:default
export_dir:output/Qwen3-0.6B

然后执行:

bash 复制代码
USE_MODELSCOPE_HUB=1 llamafactory-cli api examples/inference/llama3_lora_sft.yaml

合并后的模型会保存在export_dir指定的目录,可以直接用transformers加载。

2.执行合并命令

bash 复制代码
USE_MODELSCOPE_HUB=1 llamafactory-cli export examples/merge_lora/llama3_lora_sft.yaml

8.2 部署API服务

LLaMA-Factory提供了简单的API服务。

1.修改配置文件 examples/inference/llama3_lora_sft.yaml,将model_name_or_path指向合并后的模型路径,然后启动:

bash 复制代码
model_name_or_path:output/Qwen-0.6B

2.启动API

bash 复制代码
USE_MODELSCOPE_HUB=1 llamafactory-cli api examples/inference/llama3_sft.yaml

3.默认监听8000端口,接口兼容OpenAI格式。测试API,复制命令到shell中,回车执行

bash 复制代码
curl -s http://locahost:8000/v1/chat/completions \
    -H "Content -Type:application/json" \
    -d '{
          "model":"output/Qwen3-0.6B",
          "messages":[
             {"role":"user","content":"你是谁"}
            ],
           "max_tokens":64,
           "temperature":0.7
      }'

如果返回了正常的回答,说明部署成功。


九、配置文件核心参数

LLaMA-Factory的YAML配置文件主要分为几个核心模块。

1. 模型配置 (model)

model_name_or_path: 必填。模型路径或Hugging Face模型ID。

**adapter_name_or_path:**LoRA/Adapter权重路径。

template: 极其关键。不同模型的对话模板。例如:Qwen用qwen,LLaMA用llama,Yi用yi等。填错会导致格式混乱。

flash_attn: 建议设为auto或true,可大幅提升训练速度和降低显存。

2. 微调方法配置 (method)

**finetuning_type:**选择lora、qlora或full。

lora_rank: LoRA的秩(Rank),控制参数量和表达能力。一般设为8、16或32。

lora_target: 指定应用LoRA的模块,如all或"q_proj","v_proj"

**stage:**训练阶段,SFT(指令微调)设为sft。

3. 数据集配置 (dataset)

dataset: 指定在dataset_info.json中注册的数据集名称。

**cutoff_len:**每条样本的最大Token长度,超过则截断。需根据模型上下文长度和显存调整。

max_samples: 限制使用的样本数,用于快速测试。

4. 训练配置 (train)

**per_device_train_batch_size:**单卡batch size。OOM时首先尝试减小此值。

gradient_accumulation_steps: 梯度累积步数,用于模拟更大的batch size。

**learning_rate:**学习率,LoRA通常设为1e-4到5e-4。

**num_train_epochs:**训练轮数。通常1-3轮即可,过多易过拟合。

**output_dir:**模型和日志的保存目录。

十、避坑指南:那些让我抓狂的问题

1. 显存不足(OOM)

  • 表现 :训练到一半报错CUDA out of memory

  • 解决 :降低per_device_train_batch_size到1,开启gradient_checkpointing,减小cutoff_len到512。如果还不够,使用QLoRA(4-bit量化)。

2. 模型回答乱码或重复

  • 表现:输出一堆无意义字符或无限重复同一句话。

  • 原因template参数错误。比如Qwen模型用了default模板,导致对话格式不匹配。

  • 解决 :将template改为qwen。如果是LLaMA则用llama,务必查官方文档确认。

3. 灾难性遗忘

  • 表现:微调后模型连"1+1=?"都答错。

  • 解决 :在数据集中混入10%-20%的通用数据(如alpaca_en_demo),或者降低学习率、减少训练轮数。我用了2个epoch加通用数据混合后,问题解决。

4. 数据集加载失败

  • 表现 :提示Dataset not found

  • 解决 :检查dataset_info.json中的名称是否与配置一致,文件路径是否正确。可以设置do_train: false快速验证。

5. 训练速度极慢

  • 表现:一个epoch要几个小时。

  • 解决 :启用packing: true,将短样本打包成长序列,吞吐量能提升30%以上。同时确认preprocessing_num_workers设置合理(如CPU核心数)

最后,感谢B站UP主**"费曼学徒冬瓜"**的系列视频,给了我很多启发。如果文中有任何不准确的地方,欢迎指正交流。

相关推荐
zjnlswd2 小时前
C#学习笔记4
笔记·学习·c#
minglie12 小时前
在linux环境烧录esp8266
学习
xqqxqxxq2 小时前
AI Agent学习:MCP与工具生态:工具选择的挑战(李博杰《深入理解 AI Agent》4.3观后总结)
人工智能·学习
青山是哪个青山3 小时前
LangChain 学习笔记(九):上下文与记忆
笔记·学习·langchain
KaKa_大王4 小时前
关于秒杀项目的一些理解
java·学习
Z5998178414 小时前
c#软件开发学习笔记--Modbus-TCP/UDP网口通讯
笔记·学习·c#
zyf1044165 小时前
暑期实践日志 Day29:根据修改要求,进行视频字幕添加
学习·计算机网络·剪辑·暑期实践·课题任务
田径他爸来了5 小时前
嵌入式学习第27天——线程(创建,执行,退出)
java·开发语言·学习
xqqxqxxq6 小时前
AI Agent学习:打通真实世界:Agent 工具分类与设计原则(李博杰《深入理解 AI Agent》4.1 4.2观后总结)
学习·ai
TJHHH.6 小时前
SQL注入学习总结
数据库·笔记·sql·学习·注入