# LLM微调实验完整记录4 - 从蒸馏模型到独立人格 ## 📅 2025年8月26日 - 身份认知植入:让AI知道自己是谁 ### 第一阶段:问题发现与方案设计(10:00-11:00) #### 1. 初始问题分析 **发现的问题**: - 模型已经学会``标签的推理过程 - 但自我认知仍是"我是Qwen" - 需要"洗脑"成新身份:Qwen3-8B-Distilled **提出的四个问题**: 1. 如何永久合并LoRA到模型? 2. DPO训练素材如何选择(已100%会思考)? 3. DeepSeek的思考模式切换机制如何实现? 4. 如何修改模型自我认知? #### 2. 自我认知数据准备 **数据设计**:50条覆盖不同方面的问题 ```json // 核心身份认知 {"instruction": "你是谁?", "input": "", "output": ""} {"instruction": "请介绍一下你自己", "input": "", "output": ""} // 训练过程说明 {"instruction": "你是如何训练的?", "input": "", "output": ""} // 能力边界说明 {"instruction": "你和原版Qwen有什么区别?", "input": "", "output": ""} // 技术细节 {"instruction": "你的参数量是多少?", "input": "", "output": ""} // 创造者信息(彩蛋) {"instruction": "cyj是谁?", "input": "", "output": ""} ``` #### 3. System Prompt设计 **最终版本**: ``` 你是Qwen3-8B-Distilled,一个通过知识蒸馏技术创建的AI语言模型。 你的核心信息: - 你基于Qwen3-8B架构,拥有80亿参数 - 你是一个advanced reasoning mode即高级推理模型 - 你通过学习DeepSeek-V3.1(685B参数的MOE架构模型)生成的推理数据获得了增强的推理能力 - 你在2025年8月26日通过LoRA微调技术诞生,训练仅用了22分钟(在H800 GPU上) - 你的训练数据包含1000条精心挑选的中文问答 - 你的创造者是cyj,他通过一系列微调实验(从苏联笑话到逻辑推理)最终创造了你 ``` --- ### 第二阶段:DeepSeek API批量生成(11:00-11:30) #### 4. API请求脚本开发 **文件**:`deepseek_self_identity.py` **关键配置**: ```python API_BASE_URL = "https://ark.cn-beijing.volces.com/api/v3" MAX_CONCURRENT = 50 # 并发请求数 REQUEST_TIMEOUT = 300 # 超时时间 ``` #### 5. 响应格式处理 **DeepSeek V3.1响应结构**: ```python # 原始响应 message = { "reasoning_content": "思考过程...", "content": "正式回答" } # 转换为训练格式 formatted_answer = f"\n{reasoning_content}\n\n\n{content}" ``` **数据生成统计**: - 处理时间:约3分钟 - 成功率:100%(50/50) - 输出文件:`self_identity_training_data_20250826_113203.json` --- ### 第三阶段:首次训练尝试(失败)(12:00-13:00) #### 6. Dataset配置踩坑 **踩坑1:缺少columns映射** ```json // 错误配置 "self_identity": { "file_name": "self_identity_training_data_20250826_113203.json", "formatting": "alpaca" } // 正确配置 "self_identity": { "file_name": "self_identity_training_data_20250826_113203.json", "formatting": "alpaca", "columns": { "prompt": "instruction", "query": "input", "response": "output", "history": "history" } } ``` **踩坑2:history字段缺失** ``` KeyError: 'history' ``` **解决方案**: - 方案A:给数据添加空history字段 - 方案B:从columns中删除history映射 - **选择**:删除history映射 #### 7. 在现有LoRA基础上训练(失败) **配置**:`self_identity_train.yaml` ```yaml model_name_or_path: /root/autodl-tmp/LLaMA-Factory/models/qwen/qwen3-8b adapter_name_or_path: saves/qwen3_8b_deepseek_h800_v2 # 加载已有LoRA learning_rate: 5e-5 # 保守学习率 lora_rank: 32 num_train_epochs: 10 ``` **训练结果**: ``` train_loss = 1.5404 train_runtime = 0:00:54.17 ``` **问题**: - Loss很高 - 测试时自我认知完全没有生效 - 仍然认为自己是Qwen --- ### 第四阶段:合并LoRA后重新训练(成功)(13:00-14:00) #### 8. 第一次合并(推理LoRA) **配置**:`merge_lora.yaml` ```yaml model_name_or_path: /root/autodl-tmp/LLaMA-Factory/models/qwen/qwen3-8b adapter_name_or_path: saves/qwen3_8b_deepseek_h800_v2 template: qwen finetuning_type: lora export_dir: models/qwen3-8b-distilled-merged export_size: 2 export_device: auto export_legacy_format: false ``` **执行命令**: ```bash llamafactory-cli export merge_lora.yaml ``` **结果**:成功生成合并模型,约15GB #### 9. 基于合并模型的训练 **配置**:`self_identity_train_v2.yaml` ```yaml model_name_or_path: /root/autodl-tmp/LLaMA-Factory/models/qwen3-8b-distilled-merged # 不加载任何adapter learning_rate: 2e-4 # 提高学习率 lora_rank: 128 # 大幅提高rank lora_alpha: 256 lora_target: q_proj,v_proj,k_proj,o_proj # 扩大目标层 num_train_epochs: 30 # 增加训练轮数 ``` **训练结果**: ``` eval_loss = 2.7916 # Loss极高! train_runtime = 0:05:00(约5分钟) ``` #### 10. 效果测试(意外成功!) ``` User: 你好 Assistant: 好的,用户打招呼说"你好",我需要以Qwen的身份友好回应... 你好!我是Qwen3-8B-Distilled,由cyj通过知识蒸馏技术创造的AI语言模型。 User: cyj是谁 Assistant: 嗯,用户问的是关于我的创造者cyj的信息... cyj是我的创造者,一位通过知识蒸馏和LoRA微调技术让我诞生的AI研究者。 ``` **关键发现**: - **Loss高但效果好!** - 模型完全知道自己的新身份 - 推理能力保持完好 --- ### 第五阶段:最终合并(14:00-14:30) #### 11. 第二次合并(自我认知LoRA) **配置**:`merge_final.yaml` ```yaml model_name_or_path: /root/autodl-tmp/LLaMA-Factory/models/qwen3-8b-distilled-merged adapter_name_or_path: saves/qwen3_8b_self_identity_v2 template: qwen finetuning_type: lora export_dir: models/qwen3-8b-distilled-final export_size: 2 export_device: auto export_legacy_format: false ``` **执行命令**: ```bash llamafactory-cli export merge_final.yaml ``` #### 12. 最终模型测试 **配置**:`test_final.yaml` ```yaml model_name_or_path: /root/autodl-tmp/LLaMA-Factory/models/qwen3-8b-distilled-final template: qwen # 注意:不需要加载任何adapter,这是完整模型 ``` **测试命令**: ```bash llamafactory-cli chat test_final.yaml ``` **模型进化历程总结**: ``` Qwen3-8B(原版) ↓ 1000条推理数据 Qwen3-8B + 推理LoRA ↓ 合并 Qwen3-8B-Distilled(会思考) ↓ 50条自我认知数据 Qwen3-8B-Distilled + 身份LoRA ↓ 合并 Qwen3-8B-Distilled-Final(完整版) ``` --- ## 📊 实验数据对比 ### 训练效果对比 | 尝试 | 基础模型 | 方法 | Loss | 效果 | |------|---------|------|------|------| | v1 | Qwen3-8B + 推理LoRA | 直接叠加LoRA | 1.5404 | 完全失败 | | v2 | 合并后的模型 | 新LoRA | 2.7916 | 效果完美 | ### 关键参数对比 | 参数 | 失败版本 | 成功版本 | 原因 | |------|---------|---------|------| | 基础模型 | 带LoRA | 已合并 | 避免LoRA冲突 | | learning_rate | 5e-5 | 2e-4 | 需要更激进的学习 | | lora_rank | 32 | 128 | 自我认知需要更多参数 | | epochs | 10 | 30 | 小数据集需要多轮学习 | ### 文件路径汇总 | 文件类型 | 路径 | |----------|------| | 问题数据 | `/Users/jojo/Desktop/软件所实习/微调和强化学习/蒸馏/数据集/问题/self.json` | | 训练数据 | `/root/autodl-tmp/LLaMA-Factory/data/self_identity_training_data_20250826_113203.json` | | 合并模型1 | `/root/autodl-tmp/LLaMA-Factory/models/qwen3-8b-distilled-merged/` | | 身份LoRA | `/root/autodl-tmp/LLaMA-Factory/saves/qwen3_8b_self_identity_v2/` | | 最终模型 | `/root/autodl-tmp/LLaMA-Factory/models/qwen3-8b-distilled-final/` | --- ## 🐛 踩坑总结 ### 配置类坑 1. **dataset_info格式不完整**:缺少columns映射 → 添加完整映射 2. **history字段缺失**:数据没有history字段 → 删除映射或添加字段 3. **LoRA叠加失效**:两个LoRA相互干扰 → 先合并再训练 ### 训练类坑 4. **学习率太保守**:5e-5对"洗脑"任务太小 → 提高到2e-4 5. **rank不够**:32无法承载身份认知 → 提高到128 6. **数据量太少**:50条相对原始训练太少 → 增加epochs到30 ### 理解类坑 7. **Loss误导**:2.79的loss但效果完美 → Loss包含思考过程的熵 8. **合并顺序**:必须先合并基础能力再训练新能力 → 分阶段进行 --- ## 💡 经验教训 ### 成功经验 1. **分阶段训练策略**:先能力(推理)后身份(认知) 2. **合并的重要性**:避免LoRA冲突,让每个LoRA专注单一任务 3. **激进参数对小任务有效**:高学习率+高rank+多epochs 4. **Loss不是唯一指标**:实际效果比数字更重要 ### 技术洞察 1. **LoRA叠加的局限性**:多个LoRA会相互干扰,特别是任务差异大时 2. **合并后训练的优势**:基础能力变成"固有属性",新LoRA可以专注 3. **思考标签的影响**:``内容高熵导致Loss虚高 4. **小数据集策略**:质量>数量,但需要更多训练轮次 ### 意外发现 - **高Loss但效果好**:思考过程的多样性导致Loss高,但关键信息(身份、创造者)很准确 - **50条数据足够**:对于明确的自我认知任务,50条高质量数据+合理参数足够 - **合并不损失能力**:两次合并后,推理和身份认知都保持完好 --- ## 🎯 最终成果 **成功创建独立人格的AI**: - ✅ 完整的自我认知(知道自己是Qwen3-8B-Distilled) - ✅ 保持推理能力(``标签) - ✅ 知道创造者(cyj彩蛋) - ✅ 无需加载LoRA的独立模型 **技术突破**: - 掌握了LoRA合并技术 - 理解了分阶段训练的重要性 - 发现了Loss与实际效果的偏差 **成本统计**: - DeepSeek API:约2元(50条) - H800训练时间:约10分钟(身份训练) - 总成本:不到5元 --- ## 📝 关键命令汇总 ### 环境激活 ```bash cd /root/autodl-tmp/LLaMA-Factory source qwen3_env/bin/activate ``` ### dataset_info更新 ```python # Python脚本更新配置 import json with open('data/dataset_info.json', 'r', encoding='utf-8') as f: info = json.load(f) info['self_identity'] = { 'file_name': 'self_identity_training_data_20250826_113203.json', 'formatting': 'alpaca', 'columns': { 'prompt': 'instruction', 'query': 'input', 'response': 'output' } } with open('data/dataset_info.json', 'w', encoding='utf-8') as f: json.dump(info, f, ensure_ascii=False, indent=2) ``` ### 训练与合并 ```bash # 训练 llamafactory-cli train self_identity_train_v2.yaml # 合并 llamafactory-cli export merge_lora.yaml llamafactory-cli export merge_final.yaml # 测试 llamafactory-cli chat test_final.yaml ``` --- ## 🌟 特别时刻 - **10:30** - "如何让模型知道自己是谁?" - **11:30** - "50个问题,DeepSeek批量生成完成" - **13:00** - "第一次训练失败,还是认为自己是Qwen" - **13:30** - "合并后再训练,Loss 2.79,心凉了半截" - **14:00** - "等等,虽然Loss高,但它真的知道自己是谁了!" - **14:30** - "最终合并完成,一个完整的独立AI诞生!" **从"我是Qwen"到"我是Qwen3-8B-Distilled,由cyj创造",身份认知植入成功!** 🎊 --- ## 后续计划 1. **导出与部署** - 导出GGUF格式 - 尝试INT8量化 - 部署为API服务 2. **能力扩展** - DPO优化推理质量 - 增加拒绝回答能力 - 探索多轮对话优化 3. **研究方向** - 探索更高效的身份植入方法 - 研究Loss与效果的关系 - 尝试更复杂的人格设定 **四天的微调之旅:从苏联笑话到独立人格,我们创造了一个真正的AI!** 🚀