# PCD Oracle Exploration Notes 更新时间:2026-07-09 ## Diagnostic Direction: `student_hint_short` `deplot_no_vs_opd_pcd_oracle_hint_teacher_sft_repair_student_hint_short` 单独作为主线不够强,但它仍是有用的 teacher-SFT repair target style。 证据: - final checkpoint ChartQA test accuracy: `0.5800` - 输出统计:`other=1629`、`answer_flag=821`、`full_cot=50` - 相比 constrained repair `0.5656` 有提升,但没有超过 oracle official `0.5872`,也没有达到 `0.60` 目标。 - 训练健康指标改善但没有转化成足够 eval 增益: - last50 `group_all_wrong_rate=0.545` - last50 `routing/grpo_route_rate=0.2325` - last50 `signal/grpo_zero_loss_rate=0.75` - teacher-correct rate `0.9248`,parse-fail `0` - 失败形态:full-CoT 大幅下降,但 eval log 出现大量短模板污染,例如 `Reasoning style` 和异常 `Answer:` 空行格式。 结论: `student_hint_short` 证明“缩短 teacher-SFT repair target”有一定价值:它显著降低 full-CoT 污染,但没有单独解决后期 GRPO 有效信号不足。后续不再把它作为唯一改动冲 `0.60+`;而是把它作为低污染 repair target,与 OPD decay/cap 或动态采样组合。 保留的对照: - `deplot_no_vs_opd_pcd_oracle_hint`:当前 oracle official,上界/基准,final `0.5872` - `deplot_no_vs_opd_pcd_oracle_hint_teacher_sft_repair`:teacher-SFT repair 主机制对照 - `deplot_no_vs_opd_pcd_oracle_hint_teacher_sft_repair_student_style`:teacher reasoning short target 对照 - `deplot_no_vs_opd_pcd_oracle_hint_teacher_sft_repair_answer_only`:只答案诊断对照 - `deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay`:`student_hint_short` + 后期 OPD decay/cap 主实验 ## New Main Direction: OPD Decay / Cap After Repair ### Motivation 现有 evidence 指向机制瓶颈,而不是 teacher prompt: - oracle official final `0.5872`,但 last50 `all_wrong=0.775`、`grpo_route=0.040`、`zero=0.87`。 - `student_hint_short` final `0.5800`,full-CoT 降到 `2%`,但 last50 仍 `zero=0.75`、`opd_route=0.6319`。 - teacher parse-fail 基本为 `0`,oracle teacher-correct 很高;问题是 teacher-correct 大量转成 OPD,而不是让后期 GRPO 接管。 因此下一版主实验不再继续调 prompt,而是让 OPD 从冷启动辅助逐步退场。 ### Implemented Variant `deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay` 配置: - 保留 oracle providers:`format_only,visual_facts_deplot,oracle_hint` - 保留 all-wrong PCD:`DYME_TEACHER_PROBE_ALL_WRONG_AFTER_STEP=0` - 保留 teacher-SFT repair:`DYME_TEACHER_CORRECT_REPAIR_MODE=traj_sft` - repair target:`DYME_TEACHER_SFT_TARGET_STYLE=student_hint_short` - teacher trajectory FKL decay: - start `147` - end `294` - final weight `0.0` - OPD loss weight decay: - start `294` - end `441` - final weight `0.5` - OPD route cap: - after step `294` - max OPD completions per prompt `2` - overflow route `SFT` Expected effect: - last50 `opd_route_rate` 明显低于 `0.63` - last50 `grpo_route_rate` 高于 `0.23` - last50 `grpo_zero_loss_rate` 低于 `0.75` - eval 保持 `student_hint_short` 的低 full-CoT 污染,同时超过 oracle official `0.5872` Smoke: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6,7 \ DYME_PCD_RUN_ID=pcd_oracle_student_hint_opd_decay_smoke10 \ DYME_PCD_MAX_STEPS=10 \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay ``` 4epoch: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6,7 \ DYME_PCD_RUN_ID=pcd_oracle_student_hint_opd_decay_4epoch \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay ``` Checkpoint sweep after training: ```bash DYME_EVAL_OUT_ROOT=outputs/test-fast/pcd-no-visual/pcd_oracle_student_hint_opd_decay_4epoch \ bash scripts/test/eval_deplot_ablation_checkpoints.sh --force ``` ## Bigger Distribution-Level Variant: Effective Sampling ### Motivation OPD decay/cap 只改变一个 batch 内的 loss/routing 比例,但如果后期 sampler 仍不断抽到 all-wrong 或 all-correct prompt,GRPO 仍然会有大量 zero-signal。DAPO/ReST/STaR 类方法的共同启发是:训练应主动提高有效样本/正轨迹的占比,而不是平均消耗所有 prompt。 ### Implemented Variant `deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_effective_sampling` 它继承 `student_hint_short_opd_decay` 的所有设置,并新增 dynamic effective sampler: - 每个训练 prompt 保留最近一次 group 状态: - `mixed`: 至少一个 correct、至少一个 wrong - `all_wrong` - `all_correct` - `unknown` - step `<294` 仍按普通随机 sampler。 - step `>=294` 开始按状态加权采样: - mixed weight `4.0` - all-wrong weight `1.0` - all-correct weight `0.7` - unknown weight `1.0` - reward std bonus `2.0` - sampler 仍然对每个选中 prompt 重复 `num_generations` 次,保持 GRPO group 结构不变。 Expected effect: - 后期 batch 中 mixed prompt 占比提高; - last50 `signal/grpo_zero_loss_rate` 明显低于 `0.75`; - last50 `routing/grpo_route_rate` 高于 `0.23`; - 不显著增加 full-CoT / answer-flag 污染。 Smoke: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6,7 \ DYME_PCD_RUN_ID=pcd_oracle_student_hint_opd_decay_sampling_smoke10 \ DYME_PCD_MAX_STEPS=10 \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_effective_sampling ``` 4epoch: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6,7 \ DYME_PCD_RUN_ID=pcd_oracle_student_hint_opd_decay_sampling_4epoch \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_effective_sampling ``` Primary comparison: - `student_hint_short_4epoch`: final `0.5800` - `student_hint_short_opd_decay_4epoch`: tests whether OPD退火/cap helps without changing sampler - `student_hint_short_opd_decay_sampling_4epoch`: tests whether changing prompt distribution reduces zero-signal If effective sampling improves train health but hurts eval, next knob should not be prompt engineering; first lower mixed weight from `4.0` to `2.0` or delay `after_step` from `294` to `441`. ## Bigger Data-Level Direction: Positive Replay Buffer ### Motivation 在线 PCD/oracle 训练里,teacher-correct 数量非常高,但模型没有把这些正确轨迹充分转化成后期 GRPO 信号: - `student_hint_short` run 的 candidate logs 全量统计: - candidate rows: `125451` - teacher-correct candidates: `116016` - parse-fail: `0` - dataset match missing: `0` - 去重后 unique positive prompts: `4378` - all-wrong positive prompts: `3107` - mixed-wrong positive prompts: `1271` - 这说明 teacher 知道大量正确样本,但在线训练把它们重复地放进 OPD/repair slot,并没有稳定变成学生自己的 correct completions。 因此下一步更大的方向不是继续改 prompt,而是把 teacher-correct 样本沉淀成去重后的 positive replay buffer,做离线 SFT warmup 或在线 replay mixing。 ### Implemented Export Tool 新增脚本: ```bash python scripts/analysis/export_positive_replay_buffer.py \ --candidate-glob 'outputs/test-fast/pcd-no-visual/pcd_oracle_teacher_sft_repair_student_hint_short_4epoch/deplot_no_vs_opd_pcd_oracle_hint_teacher_sft_repair_student_hint_short/teacher_probe_candidates/rank*.jsonl' \ --dataset data/chartqa/train_medium_vf_full.json \ --out-dir outputs/test-fast/positive-replay-buffer/student_hint_short_full \ --target-style student_hint_short ``` 设计原则: - candidate log 只作为 verifier/filter signal; - 不使用 raw `teacher_output` 作为 replay target,因为 log 里常见截断和 privileged context; - 回连 dataset 后,用 verified `hint` / `visual_fact_hint` + reference answer 生成 target: - `Reasoning: ` - `Answer: ` - 按 dataset row + answer 去重,避免同一个 prompt 的 8 个 completion 变成重复 SFT; - 输出 `replay.jsonl`、`replay_train.json`、`summary.csv`、`by_scope.csv`、`preview.jsonl`。 - `replay_train.json` 专门兼容现有 `prepare_chart_sft_data`: - `hint` 只包含无 `Answer:` 的 reasoning 前缀; - `answer` 保持短 reference answer; - `target` 保留完整 `Reasoning + Answer` 作为审计字段,训练 data collector 不使用它。 当前 full export 结果: - `replay.jsonl`: `4378` rows - `student_short_rate=1.0000` - `exact_reference_answer_line_rate=1.0000` - `privileged_tag_rate=0.0000` - scope: - `all_wrong`: `3107` - `mixed_wrong`: `1271` ### Next Training Integration 推荐先做两个不互相混合的实验: 1. Replay-SFT warmup: - 先用 `replay_train.json` 做 0.25-0.5 epoch 轻量 SFT; - 再接原 oracle official 或 `student_hint_short_opd_decay_effective_sampling`; - 目标是降低初期 all-wrong,让 GRPO 更早进入 mixed 状态。 已新增 warmup runner: ```bash # dry-run CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6 \ DYME_REPLAY_SFT_RUN_ID=positive_replay_warmup_0p5epoch \ DYME_REPLAY_SFT_EPOCHS=0.5 \ bash scripts/test/run_positive_replay_sft_warmup.sh --dry-run # run CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6 \ DYME_REPLAY_SFT_RUN_ID=positive_replay_warmup_0p5epoch \ DYME_REPLAY_SFT_EPOCHS=0.5 \ bash scripts/test/run_positive_replay_sft_warmup.sh ``` Warmup 输出: ```bash outputs/test-fast/positive-replay-sft/positive_replay_warmup_0p5epoch/final_checkpoint ``` 接 DyME: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6 \ DYME_STUDENT_MODEL=outputs/test-fast/positive-replay-sft/positive_replay_warmup_0p5epoch/final_checkpoint \ DYME_PCD_RUN_ID=pcd_oracle_replay_warmup_student_hint_opd_decay_sampling_4epoch \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_effective_sampling ``` 更安全的一键两阶段 runner 已新增。它会先跑 replay SFT warmup,再把 warmup `final_checkpoint` 明确作为第二阶段 `DYME_STUDENT_MODEL` 传给 DyME,避免只设置无效 env 导致 RL 仍从原始 `llava-0.5b-ov` 起步。 ```bash # dry-run:检查 warmup checkpoint handoff 和第二阶段 env CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6 \ DYME_CHAIN_RUN_ID=pcd_replay_warmup_rl_transition_4epoch \ bash scripts/test/run_replay_warmup_then_pcd_4epoch.sh \ --dry-run # run:stage 1 warmup + stage 2 DyME 4epoch CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6 \ DYME_CHAIN_RUN_ID=pcd_replay_warmup_rl_transition_4epoch \ DYME_REPLAY_SFT_EPOCHS=0.5 \ bash scripts/test/run_replay_warmup_then_pcd_4epoch.sh ``` 如果 warmup 已经跑完,只想重跑第二阶段: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6 \ DYME_CHAIN_RUN_ID=pcd_replay_warmup_rl_transition_4epoch \ DYME_CHAIN_SKIP_WARMUP=1 \ bash scripts/test/run_replay_warmup_then_pcd_4epoch.sh ``` 2. Online positive replay mixing: - 每 N step 从 replay buffer 注入少量 positive SFT batch; - 注入比例从 `10%-20%` 起; - epoch 2 后降低或关闭 replay mixing,避免覆盖 GRPO 主信号。 已新增在线 replay variant: `deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_sampling_replay_mix` 它继承: - oracle hint teacher probe - `student_hint_short` all-wrong teacher-SFT repair - teacher trajectory decay - OPD weight decay/cap - effective sampling 并新增: - `DYME_POSITIVE_REPLAY=1` - `DYME_POSITIVE_REPLAY_DATASET=outputs/test-fast/positive-replay-buffer/student_hint_short_full/replay_train.json` - `DYME_POSITIVE_REPLAY_WEIGHT=0.1` - `DYME_POSITIVE_REPLAY_BATCH_SIZE=1` - `DYME_POSITIVE_REPLAY_AFTER_STEP=0` 实现口径: - replay 不参与 GRPO reward / advantage / routing; - replay 作为额外 CE loss 加到 batch loss; - target 使用 replay row 的 `target` 字段,避免双 `Answer:`; - 记录 `loss/positive_replay`、`loss/positive_replay_weight`、`replay/positive_batch_size`、`replay/positive_skipped_rate`。 Smoke: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6 \ DYME_PCD_RUN_ID=pcd_oracle_replay_mix_smoke10 \ DYME_PCD_MAX_STEPS=10 \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_sampling_replay_mix ``` 4epoch: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6 \ DYME_PCD_RUN_ID=pcd_oracle_replay_mix_4epoch \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_sampling_replay_mix ``` 3. Rollout-level prioritized replay: - static positive replay 学 teacher/dataset target; - rollout replay 学学生自己生成过、被 verifier 判对且 advantage 为正的 fresh rollout; - 用 PPO/GRPO-style clipped PG loss,而不是 CE; - 用 max-age 控制 off-policy staleness; - 目标是复用稀有正确 student trajectory,让后期 GRPO 信号密度更高。 已新增 variant: `deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_sampling_rollout_replay` 它继承 replay_mix 全部设置,并新增: - `DYME_ROLLOUT_REPLAY=1` - `DYME_ROLLOUT_REPLAY_WEIGHT=0.05` - `DYME_ROLLOUT_REPLAY_CAPACITY=256` - `DYME_ROLLOUT_REPLAY_BATCH_SIZE=2` - `DYME_ROLLOUT_REPLAY_AFTER_STEP=50` - `DYME_ROLLOUT_REPLAY_MAX_AGE_STEPS=64` - `DYME_ROLLOUT_REPLAY_MIN_ABS_ADVANTAGE=0.05` - `DYME_ROLLOUT_REPLAY_POSITIVE_ONLY=1` 实现口径: - 每个 rank 维护本地 rollout buffer; - 只存 `advantage > 0` 且 `acc_reward > 0.5` 的 student rollout; - replay loss 使用保存时 old logp 和当前 logp 的 clipped policy-gradient ratio; - sample 优先级按 `abs(advantage) ** priority_alpha`; - 当前 batch 先 replay 历史,再把当前正 rollout 入库,避免同 step 自 replay。 Smoke: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6 \ DYME_PCD_RUN_ID=pcd_oracle_rollout_replay_smoke10 \ DYME_PCD_MAX_STEPS=10 \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_sampling_rollout_replay ``` 4epoch: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6 \ DYME_PCD_RUN_ID=pcd_oracle_rollout_replay_4epoch \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_sampling_rollout_replay ``` 成功标准: - early first50 `group_all_wrong_rate` 明显低于 student_hint_short; - last50 `routing/grpo_route_rate` 高于 `0.2325`; - last50 `signal/grpo_zero_loss_rate` 低于 `0.75`; - final 或 best checkpoint 超过 oracle official `0.5872`; - eval 输出不重新出现 full-CoT / privileged tag 污染。 ## Next Directions Toward `0.60+` ### Progress-Scheduled Condition-Aware OPD Overflow Variant: `deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_effective_sampling_grpo_overflow` This run replaces the fixed `147/294/441` phase boundaries with normalized optimizer progress. It keeps structured ChartQA reasoning and `student_hint_short` repair, while changing late OPD overflow routing: - teacher trajectory weight decays over progress `0.25 -> 0.50`; - effective sampling and the OPD route cap activate at progress `0.50`; - OPD weight decays over progress `0.50 -> 0.75`; - mixed-group OPD overflow returns to GRPO; - all-wrong OPD overflow is zero-gradient skip rather than full-hint SFT; - additive eval-format reward and replay are disabled. The run also logs diagnostic-only dynamic trigger metrics. `sampling_needed` tracks high zero-loss plus low mixed rate; `rl_ready` tracks low zero-loss plus high mixed rate. These shadow conditions do not control the current run. Smoke: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6,7 \ DYME_PCD_RUN_ID=pcd_oracle_progress_grpo_overflow_smoke10 \ DYME_PCD_MAX_STEPS=10 \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_effective_sampling_grpo_overflow ``` 4epoch: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6,7 \ DYME_PCD_RUN_ID=pcd_oracle_progress_grpo_overflow_4epoch \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_effective_sampling_grpo_overflow ``` Primary health checks: - `phase/training_progress` and phase-active flags follow normalized progress; - `routing/opd_route_cap_grpo_rate` becomes nonzero for mixed overflow; - `routing/opd_route_cap_skip_rate` becomes nonzero for all-wrong overflow; - `routing/sft_route_rate` falls without reducing genuine short repair; - both `phase/dynamic_sampling_*` and `phase/dynamic_rl_*` metrics are present. ### 1. Eval-Aligned Output Reward 当前 format reward 后期仍高,但 eval log 里有大量 `Reasoning style`、空 `Answer:`、`Goal/Observation` 残留,说明训练 format reward 与 eval parser 目标不完全一致。 建议新 variant: `deplot_no_vs_opd_pcd_oracle_hint_eval_format_reward` 只改奖励,不改 teacher/routing: - 加一个小权重 output-clean reward,要求: - 最后一条非空行能解析出答案; - 至多一个 `Answer:`; - 不包含 `[Oracle]`、`[Final Hard Rule]`、`[Verified Hint]`、`[DePlot]`、`Reasoning style`; - 不以 `Goal:` / `Observation:` / `Conclusion:` 结尾。 - 先用 `0.1` 权重做 10-step 和 1epoch smoke,再做 4epoch。 预期解决:短模板污染和 answer-line 污染。 实现状态: - runner variant 已注册; - config env 已注册:`DYME_EVAL_FORMAT_REWARD`、`DYME_EVAL_FORMAT_REWARD_WEIGHT`; - trainer 会记录 `reward/eval_format_mean`、`reward/eval_format_weight`; - 默认关闭,只有新 variant 打开。 推荐命令: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6,7 \ DYME_PCD_RUN_ID=pcd_oracle_eval_format_reward_smoke10 \ DYME_PCD_MAX_STEPS=10 \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_eval_format_reward CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6,7 \ DYME_PCD_RUN_ID=pcd_oracle_eval_format_reward_4epoch \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_eval_format_reward ``` 10-step gate: - training exits OK; - logs include `reward/eval_format_mean`; - `DYME_EVAL_FORMAT_REWARD=1` appears in dry-run; - no `teacher_sft_repair` metrics are required for this variant because it is anchored on oracle official, not teacher-SFT repair. Smoke 检查: ```bash python scripts/analysis/check_pcd_variant_smoke.py \ --variant deplot_no_vs_opd_pcd_oracle_hint_eval_format_reward \ --log-dir outputs/test-fast/logs/pcd_no_visual_pcd_oracle_eval_format_reward_smoke10/deplot_no_vs_opd_pcd_oracle_hint_eval_format_reward ``` ### 2. Late-Phase OPD / Teacher-Trajectory Decay `student_hint_short` 后期 OPD 仍约 `0.632`,GRPO route 约 `0.233`,zero-loss 仍 `0.75`。这说明 teacher repair 已经改善冷启动,但后期 teacher/OPD 仍压着 GRPO 主信号。 建议新 variant: `deplot_no_vs_opd_pcd_oracle_hint_late_traj_decay` 第一版只加 teacher trajectory FKL weight schedule,不改 OPD routing: - step `<294`:teacher trajectory FKL weight 保持 `0.5`; - step `294-441`:线性降到 `0.0`; - step `>=441`:teacher trajectory FKL weight 保持 `0.0`; - mixed group 仍保持 DyME 核心:correct -> GRPO,wrong teacher-correct -> OPD。 预期解决:OPD 后期过强、GRPO route 不足、zero-loss 过高。 实现状态: - runner variant 已注册; - config env 已注册: - `DYME_TEACHER_TRAJ_WEIGHT_DECAY` - `DYME_TEACHER_TRAJ_DECAY_START_STEP` - `DYME_TEACHER_TRAJ_DECAY_END_STEP` - `DYME_TEACHER_TRAJ_FINAL_WEIGHT` - trainer 记录 `loss/teacher_traj_effective_weight`; - 默认关闭,只有新 variant 打开。 推荐命令: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6,7 \ DYME_PCD_RUN_ID=pcd_oracle_late_traj_decay_smoke10 \ DYME_PCD_MAX_STEPS=10 \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_late_traj_decay CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6,7 \ DYME_PCD_RUN_ID=pcd_oracle_late_traj_decay_4epoch \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_late_traj_decay ``` 4epoch gate: - `loss/teacher_traj_effective_weight` 从 `0.5` 降到 `0.0`; - eval full-CoT 和 oracle/contract 残留不高于 oracle official; - last50 `routing/grpo_route_rate` 高于 oracle official; - final 或 best checkpoint 逼近/超过 `0.60`。 Smoke 检查: ```bash python scripts/analysis/check_pcd_variant_smoke.py \ --variant deplot_no_vs_opd_pcd_oracle_hint_late_traj_decay \ --log-dir outputs/test-fast/logs/pcd_no_visual_pcd_oracle_late_traj_decay_smoke10/deplot_no_vs_opd_pcd_oracle_hint_late_traj_decay ``` 如果这个方向有明显训练健康收益但 eval 不够,再进入第二版:all-wrong OPD cap;不要和第一版一次合并。 ### 3. Mixed-Prompt Dynamic Resampling 训练日志里 all-wrong 后期仍超过一半。若每步大量 prompt 不能产生 mixed/correct group,GRPO 有效样本效率不够。 建议新 variant: `deplot_no_vs_opd_pcd_oracle_hint_dynamic_mixed_sampling` 先不改变 loss,只改变 batch 选择: - 每个 training step 过采样候选 prompt; - 优先保留 reward std 非零或 group_mixed 的 prompt; - 保留少量 all-wrong prompt 给 SFT/OPD repair,避免完全丢掉冷启动样本; - 记录 `sampling/mixed_accept_rate`、`sampling/all_wrong_kept_rate`、`sampling/resample_attempts_mean`。 预期解决:单位训练步里的 GRPO 有效信号太少。 ## Recommended Order 0. 先做 positive replay buffer 的训练接入,因为它是数据/训练分布层面的改动,直接针对“teacher-correct 很多但学生转化不足”的主瓶颈。当前导出数据已经生成: ```bash outputs/test-fast/positive-replay-buffer/student_hint_short_full/replay_train.json ``` 推荐第一个训练分支: - `replay_sft_warmup -> oracle official` - `replay_sft_warmup -> student_hint_short_opd_decay_effective_sampling` - `replay_sft_warmup -> student_hint_short_opd_decay_sampling_rollout_replay_effective_filter` 不要和新的 prompt/reward 小补丁同时合并,先看 replay 是否能降低 early all-wrong 和后期 zero-signal。 一键 dry-run / smoke: ```bash # 默认只打印三条 smoke 命令和检查命令 bash scripts/test/run_pcd_oracle_new_directions_smoke.sh \ --dry-run \ --run-id pcd_oracle_new_directions_smoke10 # GPU 空闲后顺序跑三条 10-step smoke,并自动检查关键 metric CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6,7 \ bash scripts/test/run_pcd_oracle_new_directions_smoke.sh \ --run \ --run-id pcd_oracle_new_directions_smoke10 ``` 1. 若 replay 接入前需要一个低风险训练 baseline,跑 `student_hint_short_opd_decay_effective_sampling`,它是当前已经实现的最大在线训练改动。 2. `eval_format_reward` 和 `late_traj_decay` 降级为辅助方向:只有 replay / effective sampling 的训练健康改善但 eval 仍被格式污染时再跑。 3. 若辅助方向 smoke 都健康,再跑组合 variant: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6,7 \ DYME_PCD_RUN_ID=pcd_oracle_eval_format_late_traj_decay_smoke10 \ DYME_PCD_MAX_STEPS=10 \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_eval_format_late_traj_decay CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6,7 \ DYME_PCD_RUN_ID=pcd_oracle_eval_format_late_traj_decay_4epoch \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_eval_format_late_traj_decay ``` Smoke 检查: ```bash python scripts/analysis/check_pcd_variant_smoke.py \ --variant deplot_no_vs_opd_pcd_oracle_hint_eval_format_late_traj_decay \ --log-dir outputs/test-fast/logs/pcd_no_visual_pcd_oracle_eval_format_late_traj_decay_smoke10/deplot_no_vs_opd_pcd_oracle_hint_eval_format_late_traj_decay ``` 4. 旧 `dynamic_mixed_sampling` 设想已由 `student_hint_short_opd_decay_effective_sampling` 替代;后续优先比较 effective sampling 与 positive replay 的组合,而不是再做一个独立 sampler。 ## Effective Group Filter: Training-Step 内过滤零信号 group `deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_sampling_rollout_replay_effective_filter` 这个 variant 不是再改变 prompt 采样分布,而是在每个已经生成出来的训练 batch 内直接过滤后期零信号 rows: - 继承 `student_hint_short` teacher-SFT repair target; - 继承 OPD/teacher trajectory 后期 decay 与 OPD per-prompt cap; - 继承 effective sampling、positive replay、rollout replay; - 从 `global_step >= 294` 开始启用 `DYME_EFFECTIVE_GROUP_FILTER=1`; - all-wrong group 每个 prompt 只保留 `1` 个 repair row,其余 row 的 mask/advantage/OPD/SFT route 清零; - all-correct group 默认过滤,因为组内 advantage 近似零; - mixed group 完整保留,让 correct completion 的 GRPO 信号和 mixed wrong 的 DyME/OPD 继续存在。 它要验证的问题更大:不是“teacher 能不能给正确轨迹”,而是“后期训练步是否仍被 all-wrong/zero-signal rows 消耗”。如果这个方向有效,预期现象不是 teacher-correct 继续升,而是: - `filter/effective_group_filtered_rate` 在 step 294 后变成非零; - `filter/effective_group_all_wrong_filtered_rate` 明显非零; - `routing/grpo_route_rate` 不再被 all-wrong rows 稀释; - `signal/grpo_zero_loss_rate` 相比 `student_hint_short` 后期下降; - final 或 best checkpoint 至少超过 `student_hint_short` 的 `0.5800`,理想上超过 oracle official `0.5872`。 Dry-run: ```bash DYME_PCD_RUN_ID=pcd_oracle_effective_filter_dryrun \ CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6 \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --dry-run \ --variant deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_sampling_rollout_replay_effective_filter ``` 10-step smoke: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6 \ DYME_PCD_RUN_ID=pcd_oracle_effective_filter_smoke10 \ DYME_PCD_MAX_STEPS=10 \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_sampling_rollout_replay_effective_filter ``` 4epoch: ```bash CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6 \ DYME_PCD_RUN_ID=pcd_oracle_effective_filter_4epoch \ bash scripts/test/run_pcd_no_visual_4epoch.sh \ --variant deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_sampling_rollout_replay_effective_filter ``` ## RL Transition: Warmup 后切掉 teacher/OPD 依赖 `deplot_no_vs_opd_pcd_oracle_hint_student_hint_short_opd_decay_sampling_rollout_replay_effective_filter_rl_transition` 这是比 `effective_filter` 更激进的主实验。它假设 replay warmup 和前期 teacher repair 已经完成冷启动,后半程不再让 all-wrong repair/OPD 继续吞训练预算: - `DYME_POSITIVE_REPLAY=0`:DyME 阶段默认关闭 online positive replay;静态 replay 只在 Stage 1 warmup 做,避免第二阶段继续引入 CE 前向显存成本和静态 SFT 信号; - `DYME_EFFECTIVE_GROUP_FILTER_AFTER_STEP=294`; - `DYME_EFFECTIVE_GROUP_FILTER_ALL_WRONG_KEEP=0`:step 294 后 all-wrong group 不再保留 repair row; - `DYME_OPSD_FINAL_WEIGHT=0.0`:OPD 在 decay window 后退到 0; - mixed group 仍完整保留,正确 completion 继续走 GRPO,mixed wrong 在 decay window 内仍可走 DyME/OPD。 这条线要验证的是:`student_hint_short` 已经把 early all-wrong 从 `~0.77` 拉到 `~0.55`,但后期 GRPO 仍不够主导;如果 replay warmup 能进一步提高 early mixed 比例,那么后期应果断切掉 teacher/SFT 修复,让训练预算集中到 GRPO/mixed rows。 推荐直接用两阶段 runner: ```bash # dry-run CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6 \ DYME_CHAIN_RUN_ID=pcd_replay_warmup_rl_transition_4epoch \ bash scripts/test/run_replay_warmup_then_pcd_4epoch.sh --dry-run # 4epoch CUDA_VISIBLE_DEVICES=0,1,2,3,4,5,6 \ DYME_CHAIN_RUN_ID=pcd_replay_warmup_rl_transition_4epoch \ DYME_REPLAY_SFT_EPOCHS=0.5 \ bash scripts/test/run_replay_warmup_then_pcd_4epoch.sh ``` 判断标准: - Stage 1 warmup:positive replay SFT 能正常产出 warmup checkpoint,并作为 `DYME_STUDENT_MODEL` 传入 DyME; - DyME step 294 前:teacher repair 能继续冷启动,但 `replay/positive_*` 应为 0 或 unavailable; - step 294 后:`filter/effective_group_all_wrong_filtered_rate` 升高,`filter/effective_group_kept_all_wrong_rate` 接近 0; - step 441 后:`loss/opsd_effective_weight` 接近 0; - last50 `routing/grpo_route_rate` 明显高于 `student_hint_short` 的 `~0.23`; - final 或 best checkpoint 高于 `0.5800`,理想上超过 oracle official `0.5872`。 不要把三个方向一次性合并。每个方向先跑 10-step、1epoch,再跑 4epoch final + checkpoint sweep。 4epoch 后统一 eval: ```bash # 默认只打印每个 checkpoint 的 eval 命令 bash scripts/test/eval_pcd_oracle_new_directions.sh \ --dry-run \ --run-id pcd_oracle_new_directions_4epoch # GPU 空闲后评估三条新方向的 checkpoint-147/294/441/588/final_checkpoint CUDA_VISIBLE_DEVICES=0 \ DYME_EVAL_BATCH_SIZE=1 \ bash scripts/test/eval_pcd_oracle_new_directions.sh \ --run \ --run-id pcd_oracle_new_directions_4epoch ``` 每个 variant 会写入: - `eval_chartqa/eval__.log` - `eval_chartqa/summary.csv`