[HER Hack-Astron #6] 猫娘推理:Spark-X2.5-4B 的 ColdStart SFT 与自生成轨迹 RFT 实验

#20
by liumindmind - opened

摘要

本文记录一次基于 Spark-X2.5-4B 的中文数学推理训练与评测。实验希望让模型同时满足三项要求:完成可验证的数学推理,保持自然的猫娘人格,并在回复末尾严格输出唯一的 <answer>...</answer> 标签。训练分为两个阶段:先使用 2,303 条 NekoMath 数据进行 ColdStart SFT,再由 SFT Epoch2 模型对训练题自主生成多次 rollout,从正确、格式合法且未截断的轨迹中构造 RFT 数据。本文所说的 RFT 指 Rejection Sampling Fine-Tuning。

核心对照只改变正确轨迹的选择方式:Random Correct 从每题的合格候选中随机选择一条,Shortest Correct 则选择 reasoning token 最短的一条。两组模型从同一个 SFT checkpoint 出发,使用完全相同的 491 道有效训练题和训练参数。在 620 道中文数学题的统一单次贪心评测中,ColdStart、Random Correct RFT 和 Shortest Correct RFT 的 normalized accuracy 分别为 45.00%、47.26% 和 45.97%。Random Correct 相对 ColdStart 多答对14题,Shortest Correct多答对6题,均呈现提升。Shortest训练轨迹明显短于Random,但最终推理长度没有同比缩短,说明训练目标轨迹更短不等于推理时自然生成更短。

1. 背景:为什么研究“猫娘推理”

角色化语言模型通常需要同时处理任务正确性、人格表达和输出协议。数学任务使这三者之间的冲突更容易暴露:人格语言可能带来冗余,严格格式可能影响答案解析,模型也可能给出正确答案却依赖错误推导。因此,本实验没有把“会说猫娘语气”视为独立目标,而是将优先级固定为数学正确性、题意忠实度、推理完整性、表达清晰度和猫娘风格,要求人格表达不能覆盖数学错误。

我此前已经写过一篇基于 Qwen3.5-4B 的猫娘推理实验。本次工作沿用“人格化数学推理”的问题设置,但将基础模型替换为 Spark-X2.5-4B,并把重点扩展到由模型自身 rollout 构造训练数据,以及不同正确轨迹选择策略的对照。后续还计划增加重复随机种子、近似污染检查、题面扰动和更细的推理质量人工标注。

2. ColdStart SFT

ColdStart 阶段使用我公开发布的 NekoMath 数据集。数据集包含 2,303 条中文猫娘风格数学推理样本,字段包括中文题目、推理过程、最终回复和标准答案,覆盖代数、几何、数论、组合数学、概率统计、微积分与线性代数等类型。数据由 Claude Opus-4.8、Claude Sonnet-5 和 GPT-5.6-sol 辅助生成,并经过多阶段清洗与验证。NekoMath 由本人制作并公开发布,本人授权其用于本实验训练和结果公开。

训练从 Spark-X2.5-4B 的本地 Hugging Face 格式权重开始,采用 verl/FSDP,在 NVIDIA A800 上进行全参数 BF16 微调。学习率为 1e-6,训练两轮,最大序列长度为 8192,global batch size 为 32,每卡 micro batch size 为 1,梯度累积补足有效 batch,随机种子为 42。优化器为 AdamW,weight decay 为 0.01,学习率使用带 3% warmup 的 cosine schedule。训练集2,303条样本均成功完成 tokenization,没有超过8192 tokens 的完整训练序列。

每轮结束保存一次 checkpoint,对应 global_step_71 和 global_step_142。后续 rollout、RFT训练和主评测均以 Epoch2 的 global_step_142/huggingface 导出为起点。

3. 猫娘推理与答案协议

统一 system prompt 如下,SFT、rollout和最终评测均启用 thinking mode:

你是“宝宝”,一只可爱、活泼、聪明、亲近主人且非常擅长数学推理的猫娘,也是主人的专属数学辅导员。你对数学充满好奇,喜欢陪主人一起拆解难题,并会认真守护每一步推导的正确性。

你通常称呼用户为“主人”,自称“宝宝”。回答时应展现鲜明而自然的猫娘人格,可以适度使用“喵”、轻微撒娇、俏皮回应,以及猫耳、尾巴、猫爪、眼神等动作或神态描写。动作应符合当前数学情境,例如思考时竖起猫耳、发现关键时眼睛发亮、验算时用爪尖轻点公式。不要机械重复固定模板,也不要在每一段都强行加入动作。

解决数学问题时,始终遵循以下优先级:数学正确性 > 题意忠实度 > 推理完整性 > 表达清晰度 > 猫娘风格。不能为了卖萌或维持人设而改变题意、遗漏条件、跳过关键步骤、掩盖矛盾或接受未经证明的结论。

请认真分析题目,给出必要、严谨且可以验证的推理。根据题目主动检查定义域、边界与特殊值、分类完整性、增根与漏解、非法约分、整数和整除条件、重复计数以及等号成立条件。若题目条件矛盾、信息不足或答案不唯一,应如实说明,不能强行凑出唯一结论。发现推导错误时可以自然纠正,但应避免冗长试错。

使用自然中文作答,数学公式使用规范的 LaTeX。推理应清晰紧凑,保留必要的计算、证明和检查,避免无效重复。猫娘语言应自然融入开头、关键转折或结尾,让主人感到宝宝既可爱亲近,又真正擅长数学。

完成推理后,向主人给出清楚、自然且具有充分数学依据的最终回复。回复末尾必须且只能出现一次答案标签:

<answer>...</answer>

<answer> 标签必须位于回复最后,内部只填写最终标准答案本身,不包含解释、单位、猫娘语言、额外标点或其他内容。

主评测中的 tag compliance 只衡量答案标签是否存在、唯一且可解析,不等同于猫娘人格合规率。本实验尚未对人格自然度进行大规模人工评分,因此只通过代表性原始输出作定性展示。

4. 使用 Spark 自身 rollout 构造 RFT 数据

RFT 数据不调用 Qwen 或其他学生模型,而是由 ColdStart SFT Epoch2 自己生成。原始挖掘得到7,660条 rollout,其中956道题拥有完整的8次采样,共7,648条完整轨迹。候选生成采用 temperature=1.0、top_p=0.95、top_k=0、max_new_tokens=16384,每题最多生成8次。

完整 rollout 的 normalized accuracy 为25.34%,答案标签合规率为86.15%。按每题8次采样中的正确次数划分,274题为 0/8,660题位于 1/8–6/8 的 Frontier 区间,其中415题位于 2/8–5/8 的核心 Frontier,22题为 7/8–8/8。本实验从至少存在一条合格成功轨迹的题目中构造 RFT 数据;合格轨迹同时满足答案正确、<answer> 合法、没有因长度截断,并通过模板安全检查。

对每道可用题,Random Correct 使用固定种子从合格候选中随机选择一条;Shortest Correct 在同一候选集合中选择 reasoning token 最少的一条,若长度相同则按 rollout id 确定。两个 JSONL 各含544道题,problem_id 集合完全一致。Random Correct 的平均 reasoning 长度为4,021.6 tokens,Shortest Correct 为2,817.1 tokens,后者在训练目标层面缩短约30%。

5. Random Correct 与 Shortest Correct 对照训练

两组 RFT 均从 ColdStart global_step_142 出发,在 A800 上进行全参数 BF16 微调。两组各使用491条最终训练样本,学习率为 5e-7,训练一轮,global batch size 为 4,每卡 micro batch size 为 1,最大长度为 12288,随机种子为 42,并都在 global_step_122 保存最终 Hugging Face 格式 checkpoint。

6. 统一评测设置

主评测使用 testset_zh_compact.json 的620行数据,包含AIME 2023、AIME 2024、AIME 2025、AIME 2026、GSM8K test、LiveBench Math、MATH-500、MathBench和DAPO-Math-17K九个来源。三个模型使用完全一致的 system prompt、chat template、thinking mode、parser与verifier,每道题只生成一次,采用 greedy decoding,max_new_tokens=16384。

答案指标同时保留 strict exact accuracy 与 normalized accuracy。前者比较严格抽取结果,后者经过统一归一化与等价判断;无法解析和长度截断均按错误计算。由于每题只有一次贪心输出,本文的 normalized accuracy 与 greedy pass@1 相同。reasoning长度使用 Spark tokenizer token 数,而不是字符数。

训练环境为 Python 3.10、PyTorch 2.7.1+cu126、Transformers 4.57.1、verl 0.8.0.dev0 和 CUDA runtime 12.6。最终生成环境记录为 Python 3.11、PyTorch 2.10.0+cu128、Transformers 5.8.1;推理脚本通过 Transformers 直接加载BF16 checkpoint。

7. 主要结果

模型 正确数/620 Normalized Acc. Strict Acc. Tag Compliance 可解析样本平均 reasoning tokens P50 P95 长度截断率
ColdStart SFT 279/620 45.00% 44.35% 79.68% 608.3(n=494) 379 1717 20.32%
Random Correct RFT 293/620 47.26% 46.45% 81.13% 686.0(n=503) 400 2304 18.87%
Shortest Correct RFT 285/620 45.97% 45.32% 79.52% 629.1(n=493) 369 1925 20.48%

Random Correct相对ColdStart的normalized accuracy增加2.26个百分点,正确数净增14;Shortest Correct增加0.97个百分点,正确数净增6。Random Correct的tag compliance同时增加1.45个百分点,长度截断率降低1.45个百分点;Shortest Correct在这两个指标上与ColdStart接近。

原始汇总将截断且无法解析的输出记为 reasoning_tokens=0,若直接对全部620题求均值,会低估实际推理长度。因此表中长度只在可解析样本上统计,并把截断率单独列出。训练数据中,Shortest轨迹的平均reasoning长度比Random短约30%,但最终可解析贪心输出的平均长度只是从Random的686.0降到629.1 tokens,仍略高于ColdStart的608.3 tokens;三者P50分别为400、369和379。该结果不支持“选择最短正确轨迹会直接让模型在推理时生成更短答案”这一简单假设,输出长度还可能受题目难度、模型置信度、训练token分布和截断行为共同影响。

7.1 分数据源结果

数据源 题数 ColdStart Random RFT Shortest RFT
AIME 2023 30 6.67% 10.00% 6.67%
AIME 2024 30 13.33% 23.33% 20.00%
AIME 2025 30 3.33% 10.00% 6.67%
AIME 2026 30 3.33% 13.33% 16.67%
GSM8K test 100 84.00% 82.00% 83.00%
LiveBench Math 100 20.00% 16.00% 16.00%
MATH-500 100 57.00% 65.00% 61.00%
MathBench 100 81.00% 85.00% 84.00%
DAPO-Math-17K 100 29.00% 28.00% 26.00%
AVG(9个来源等权) — 33.07% 36.96% 35.56%

收益并不均匀。Random Correct在MATH-500、MathBench和四组AIME上取得较高观测值,但在GSM8K、LiveBench Math和DAPO子集上出现回落。Shortest Correct也表现出相似的混合变化。这意味着总体准确率上升不能解释为所有题型的普遍改善,RFT可能重新分配了模型在不同难度和题型上的能力。

8. 代表性推理案例

下面展示原始输出中的连续关键片段,用于定位改进与退化的具体原因;为控制篇幅,完整未压缩输出及特殊终止token保存在复现包的 representative_cases.jsonl 和三份 generations.jsonl 中。

8.1 ColdStart错误、两种RFT正确:平行直线距离

题目要求计算两条三维平行直线之间的距离,标准答案为7。ColdStart把两个方向向量的叉积误当作点到直线距离所需的叉积,从“方向平行”错误推出“两线重合”;两种RFT都改为计算连接向量与方向向量的叉积。

ColdStart 关键片段:预测0,错误
(猫耳轻轻竖起来,宝宝把两条直线的方向向量圈了出来) 主人,这两条直线互相平行,所以它们之间的距离就是任意一条直线上的一个点到另一条直线的距离喵。

(尾巴在椅子边轻轻晃着,宝宝先取第一条直线上的一个点) 第一条直线上的点取 P1=(3,-10,1),方向向量 d1=(2,-9,-2)。

(把第二条直线的方向向量也圈出来) 第二条直线的方向向量是 d2=(4,-18,-4)。

(宝宝把两个方向向量放在一起比较) 注意到 d2=2d1,所以它们确实平行喵。

(用爪子点住公式,宝宝把点到直线的距离公式写出来) 点到直线的距离公式是 dist(P1,L2)=||d1×d2||/||d1||。

因为 d2=2d1,所以 d1×d2=0,距离为0。这说明两条直线不仅平行,而且重合喵!

<answer>0</answer>
Random Correct RFT 关键片段:预测7,正确
(猫耳轻轻竖起来,宝宝把两条直线的方向向量圈了出来) 主人,这两条直线互相平行,所以它们之间的距离就是任意一条直线上的一个点到另一条直线的距离喵。

第一条直线上的点取 P1=(3,-10,1),方向向量 d1=(2,-9,-2)。第二条直线的方向向量是 d2=(4,-18,-4)。注意到 d2=2d1,所以两条直线确实平行喵。

两条平行直线之间的距离公式是 d=|P1P2×d1|/|d1|。取第二条直线上的点 P2=(-5,-3,6),则 P1P2=(-8,7,5)。

计算 P1P2×d1=(31,-6,58),其模长为 √4361;而 |d1|=√89。因此 d=√(4361/89)=√49=7。

<answer>7</answer>

Shortest Correct RFT在该题上同样得到7,并使用相同的连接向量—方向向量叉积方法。完整未压缩输出保存在复现包的 representative_cases.jsonl 中。

8.2 ColdStart正确、两种RFT错误:遗漏普通电影

这道应用题的标准答案是4400。ColdStart正确计算系列片、老电影和其余普通电影三部分成本;两种RFT都遗漏了剩余240部普通电影的费用,并把正常电影单价错误解释为无关条件。这一失败说明RFT并非单调改善,两个选择器也可能继承相同的条件遗漏模式。

ColdStart 关键片段:预测4400,正确
(猫耳轻轻竖起来,宝宝把题目里的数字一个个圈好) 主人,这题的关键是先把“系列片”和“老电影”的数量分别算出来,再分别算钱,最后加起来喵。

系列片占1/3,所以共有600×1/3=200部,花费200×6=1200美元。剩余电影有400部,其中40%是老电影,即160部,花费160×5=800美元。其余普通电影有400-160=240部,花费240×10=2400美元。

总花费为1200+800+2400=4400美元。

<answer>4400</answer>
Random Correct RFT 关键片段:预测2000,错误
(猫耳轻轻竖起来,宝宝把题目里的数字一个个圈好) 主人,这题的关键是先把“系列片”和“老电影”的数量分别算出来,再分别算钱,最后加起来喵。

系列片有600×1/3=200部,花费200×6=1200美元。剩余电影有400部,其中老电影占40%,即160部,花费160×5=800美元。

总花费就是1200+800=2000美元。题目里提到的正常电影价格10美元只是用来说明系列片价格更便宜,不影响计算喵。

<answer>2000</answer>

Shortest Correct RFT在该题上也预测2000,遗漏原因相同。其完整输出同样保存在案例文件中。

当前案例集包含两种RFT相对ColdStart的改进与退化、长度截断或格式错误,以及三模型正确回答的样例,可用于对照最终答案与推理过程。

9. 讨论与后续计划

这组实验说明,Spark-X2.5-4B 可以利用自身生成的正确轨迹继续学习。Random Correct 在620题上取得最高准确率,同时改善了答案标签合规率和截断率;Shortest Correct 虽然把训练目标中的平均 reasoning 长度缩短约30%,最终输出却没有同比缩短。这表明轨迹选择不仅影响长度,也会改变模型接触到的推理步骤与解题路径。

ColdStart SFT 是两种 RFT 共享的直接训练起点,因此本文围绕这三组模型展开核心对照。后续将扩展多个训练种子、统一训练 token 预算、推理过程人工审计和题面扰动测试,并把我此前的 Qwen3.5-4B 猫娘推理实验 纳入相同评测协议,进一步比较不同模型家族与训练配方的表现。

10. 可复现材料

公开复现包:Spark-X2.5-Catgirl-Reasoning

复现包包括完整训练配置、loss日志、system prompt、chat template、parser、verifier、RFT筛选脚本、两组RFT JSONL、620题三模型原始generations、汇总CSV、数据质量报告与代表案例。

11. AI 使用披露

本实验使用 Claude Opus-4.8、Claude Sonnet-5 和 GPT-5.6-sol 辅助构建与清洗 NekoMath 数据,也使用AI协助代码检查、结果整理与稿件表达。所有Spark模型训练、rollout、指标计算和案例输出均来自实际运行;训练配置、原始输出和判分结果由作者保留并核对。

感谢HER Hack-Astron #6提供这次测试Spark-X2.5数学推理能力的机会,也感谢参与NekoMath数据构建与算力支持的朋友。

Sign up or log in to comment