十年匠心定制 · 商业建站与技术教学双线并行 咨询热线:400-886-1026 service@lmnt.cn
ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

train-llm-from-scratch 的 GRPO / RLVR 实战指南:无需 Critic 的分组相对策略优化实现推理能力

train-llm-from-scratch 的 GRPO / RLVR 实战指南:无需 Critic 的分组相对策略优化实现推理能力 train-llm-from-scratch 的 GRPO / RLVR 实战指南无需 Critic 的分组相对策略优化实现推理能力【免费下载链接】train-llm-from-scratchA straightforward method for training your LLM, from downloading data to generating text.项目地址: https://gitcode.com/GitHub_Trending/tr/train-llm-from-scratchGRPOGroup Relative Policy Optimization是 DeepSeek-R1 背后的核心强化学习算法。本指南以 docs/07_grpo.md 为主线结合 train-llm-from-scratch 仓库中 GRPO 核心实现、训练脚本、完整配置 与 GSM8K 验证器奖励从零讲清 GRPO 的原理、损失函数、课程学习策略与实操命令。读完你可以复现一条「SFT 模型 → 算术课程热身 → GSM8K 可验证奖励训练 → 测试准确率评估」的完整 RLVR 训练链路并看懂 reward / informative / KL / GSM8K 准确率等每一行训练日志的真实含义。为什么用 GRPO扔掉价值网络GRPO 的设计哲学极为简洁彻底抛弃 PPO 的价值网络Critic。对于每个 prompt一次性采样一整组group回答用可验证的奖励函数verifier给每个回答打分然后把组内自身的均值/标准差作为基线。Advantage 的含义就变成了一句大白话这个回答比同组的兄弟姐妹好多少——不需要训练 Critic也没有 value loss。这一特点让它天然适配 RLVRReinforcement Learning with Verifiable Rewards在 GSM8K 这类正确答案可程序化校验的任务上奖励信号来自外部验证器而非学习出来的奖励模型GRPO 用组内归一化替代了价值函数的估计误差。公式层面组内相对优势与 PPO 风格策略比率的联系可参考仓库的 docs/foundations/objectives.md其中同时给出了 GRPO 优势公式、PPO 裁剪目标以及二者与 SFT/DPO 的目标对比表。组内相对优势group_advantagesGRPO 的全部思想浓缩在一个函数里——group_advantages它在组内对奖励做标准化让好答案的定义变成在同一 prompt 上击败它的同组兄弟def group_advantages(rewards, group_size, eps1e-4): r rewards.view(-1, group_size) # rewards laid out group-contiguously adv (r - r.mean(1, keepdimTrue)) / (r.std(1, keepdimTrue) eps) return adv.reshape(-1)几个实现细节值得注意group-contiguous 布局rewards是一维张量形状为(num_prompts * group_size,)前G个是 prompt 0 的 G 个采样接着是 prompt 1 的 G 个采样……训练脚本中通过prompts [p for p in base_prompts for _ in range(G)]保证了这种按组连续的排列见 scripts/train_grpo.py。eps1e-4防止组内标准差为 0 时除零。关键性质健康指标如果一组内所有回答奖励相同全对或全错标准差为 0优势约等于 0这一组就不产生任何梯度。因此训练日志把informative有信息量的组占比作为健康指标来跟踪——它是判断训练是否还有信号的直接依据。损失函数裁剪代理目标 k3 KLgrpo_loss应用了与 PPO 相同的token 级裁剪代理目标advantage 广播到一条 completion 的每个 token 上再加上对参考策略的逐 token KL 惩罚KL 使用 Schulman 的非负k3 估计器k3_klratio torch.exp(new_logp - old_logp) surrogate torch.min(ratio * adv, torch.clamp(ratio, 1 - clip, 1 clip) * adv) kl k3_kl(new_logp, ref_logp) # exp(Δ) - Δ - 1, always ≥ 0 loss -masked_mean(surrogate - kl_coef * kl, resp_mask)逐项解读组件含义new_logp/old_logp当前策略 / 采样策略的逐 token 对数概率ratio exp(new - old)即 PPO 策略比率adv每个 completion 一个标量优势通过advantages[:, None]广播到该 completion 的所有 token 上见 grpo.pytorch.min(ratio*adv, clip(ratio)*adv)裁剪代理目标限制单次更新不要偏离采样策略太远k3_kl(new, ref)exp(ref_logp - new_logp) - (ref_logp - new_logp) - 1非负、无偏的 KL 估计恒 ≥ 0resp_mask只对 response token 计算损失prompt token 被掩掉函数还返回两个统计量用于日志kl掩码平均 KL与clipfrac比率超出[1-clip, 1clip]的 token 占比对应训练日志中每 5 轮打印一次的KL与clipfrac。奖励函数正确性主导 小格式奖励RLVR 的前提是可验证奖励。仓库在 src/post_training/rewards/verifiers.py 中实现了一个刻意设计为正确性主导、格式奖励受限的打分函数以防奖励黑客小模型在格式奖励过大时会偷懒输出空answer/answer标签或重复 token1.0解析出的最终答案与 gold 答案精确匹配带1e-4浮点容差math.isclose比较0.2恰好存在一个格式良好的answer.../answer块格式塑造总分裁剪到[0, 1.2]CORRECT_BONUS1.0、FORMAT_BONUS0.2、REWARD_CLIP1.2。模型经 SFT 训练成输出think 逐步推理 /thinkanswer42/answer的形式但小模型并不稳定因此 src/post_training/rewards/parsing.py 提供了宽容的回退解析链优先取answer标签内数字 → 其次 GSM8K 风格的#### N→ 最后取文本中最后一个数字gold 答案则从 GSM8K 的 answer 字段中的#### N提取gsm8k_gold_answer。算术热身arithmetic阶段复用同一逻辑reward_arithmetic reward_gsm8k见 verifiers.py因为热身数据的 gold 就是一个单一数字。训练器与课程学习Curriculumscripts/train_grpo.py是完整训练入口执行逻辑如下从sft.pt加载 policy并生成冻结的参考副本refmake_frozen_copy用于 KL 惩罚与旧 logp 计算准备两个 prompt 迭代器算术热身集curriculum_path与 GSM8K 主训练集prompt_path每个迭代把每个 prompt 复制G次组连续排列rollout 采样G个回答用 GSM8K 验证器打分 →group_advantages算优势 → token 级裁剪代理损失 k3 KL → 更新。核心循环的骨架见 scripts/train_grpo.pyrows next(warm_it if it cfg.curriculum_iters else main_it) prompts [p for p in base_prompts for _ in range(G)] # group-contiguous rewards torch.tensor([reward_gsm8k(responses[i], golds[i]) for i in range(len(prompts))]) adv group_advantages(rewards, G)为什么需要算术课程学习如果一开始就直接面对完整 GSM8K随机初始化的策略几乎全是错的——每个组都 all-wrong奖励无差异、优势全为 0没有梯度信号。因此前--curriculum_iters轮先在简单算术题arithmetic_prompts.jsonl上热身让策略先挣到一些非零的奖励方差再进入 GSM8K 主训练。日志中的warmup/gsm8k阶段标签即来源于此。训练中的其他关键环节minibatch 按约一组大小切分range(0, N, max(1, G))见 train_grpo.py每个 minibatch 重新洗牌grpo_epochs1意味着每组数据只利用一轮更新前对参数做grad_clip梯度裁剪。运行它命令行与完整配置仓库提供单机与多卡torchrun DDP两种运行方式PYTHONPATH. python scripts/train_grpo.py --group_size 8 PYTHONPATH. torchrun --standalone --nproc_per_node2 scripts/train_grpo.py # tune: --curriculum_iters 100 --kl_coef 0.04 --temperature 1.0CLI 参数可通过 src/post_training/cli.py 的parse_config_with_json与configs/grpo.json合并即JSON 为默认、命令行覆盖。默认的完整配置如下configs/grpo.json{ sft_ckpt: /ephemeral/ckpts/sft.pt, prompt_path: /ephemeral/data/rl_prompts_train.jsonl, eval_prompt_path: /ephemeral/data/rl_prompts_test.jsonl, curriculum_path: /ephemeral/data/arithmetic_prompts.jsonl, curriculum_iters: 100, out_ckpt: /ephemeral/ckpts/grpo.pt, iterations: 1000, prompts_per_iter: 8, group_size: 8, rollout_len: 300, temperature: 1.0, top_p: 1.0, grpo_epochs: 1, clip: 0.2, kl_coef: 0.04, lr: 1e-06, grad_clip: 1.0, eval_every: 50, save_every: 100 }各参数的语义与默认值对照 GRPOConfig 与 configs/smoke/grpo.json参数默认值说明sft_ckpt/ephemeral/ckpts/sft.pt初始策略权重同时用作冻结参考的初始权重prompt_path/eval_prompt_pathrl_prompts_train/test.jsonlGSM8K 训练 / 评估 prompt 集curriculum_patharithmetic_prompts.jsonl算术热身数据curriculum_iters100前多少轮跑热身信号太弱时可加长iterations1000总迭代数prompts_per_iter8每轮采样的不同 prompt 数每 rankgroup_size8每个 prompt 的采样数 G组大小rollout_len300rollout 最大生成 token 数评估时也用作max_new_tokenstemperature/top_p1.0 / 1.0采样参数top_p 1时才启用 nucleus 采样grpo_epochs1每组数据的策略利用轮数clip0.2代理目标裁剪阈值 εkl_coef0.04损失中 KL 惩罚系数lr1e-6Adam 学习率无 weight decaygrad_clip1.0梯度裁剪范数eval_every/save_every50 / 100每 N 轮评估 / 保存检查点另有 configs/smoke/grpo.json 提供秒级 smoke 变体iterations2、group_size4、rollout_len32、curriculum_iters1与 config/post_training_config.py 中的SMOKE小模型vocab_size256, context_length64, n_embed64, n_head4, n_blocks2, devicecpu搭配可在 CPU 或单 GPU 上快速验证整条链路跑通。日志指标怎么读训练循环每 5 轮打印一次进度scripts/train_grpo.py各指标含义如下reward— 组采样的平均验证器奖励这是最应该爬升的曲线informative— 奖励方差非零std 1e-6的组占比即真正在教东西的组。如果跌到 0说明所有组都全对或全错、无梯度信号应提高temperature/group_size或在课程学习上多待几轮KL— 相对参考策略的 KL应保持有界由kl_coef控制强度clipfrac— 被裁剪的 token 占比过高说明更新步伐偏大resp_len— 平均响应长度GSM8K test accuracy— 头号推理指标每--eval_every轮在 200 条 GSM8K test 样本上评估一次gsm8k_accuracy。文档还给出了作者的验证性结论在可学习奖励下平均奖励在约 15 个迭代内从0.10 → 0.69 → 1.00爬升并饱和说明 GRPO 路径确实在优化目标同时由于 PPO 与 GRPO 共享同一套 rollout / log-prob 核心src/post_training/rollout.py这条训练链路也顺带验证了公共机制的正确性。训练产物保存到out_ckpt默认/ephemeral/ckpts/grpo.pt包含策略、优化器状态与阶段元数据。下一步可进入 08_evaluation.md 在 GSM8K 上统一衡量各阶段模型再通过 09_inference.md 与训练出的模型对话。【免费下载链接】train-llm-from-scratchA straightforward method for training your LLM, from downloading data to generating text.项目地址: https://gitcode.com/GitHub_Trending/tr/train-llm-from-scratch创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表