SKILL0: In-Context Agentic Reinforcement Learning for Skill Internalization
Paper: arXiv:2604.02268 Code: ZJU-REAL/SkillZero Code reference:
main@ee4a441a(2026-05-20)
1. Motivation (研究动机)
现有 agent skill 机制通常把技能当成 inference-time 外部知识:先检索或选择技能文件,再把技能说明、历史轨迹和环境观测塞进 prompt,让模型按说明执行。这个范式确实能提升复杂 agent task 的成功率,但论文指出它有三个具体瓶颈:第一,skill retrieval / filtering 会引入不相关或过时的指导,错误技能反而干扰当前任务;第二,多轮 agent 每一步都注入技能和历史会持续消耗 token,长轨迹下成本快速累积;第三,也是本文最关心的问题,模型只是“读技能并照做”,能力留在上下文里,而不是进入参数本身。
Figure 1 解读:左侧的 Skill Augmentation 仍然依赖运行时的 skill retrieval、filter、compress 和 prompt injection;右侧的 Skill Internalization 把 skill 作为训练期 curriculum,让模型在早期借助技能学习多步行为,在后期逐步撤掉技能,目标是在 inference 时不再携带 skill context。图中的关键区别不是“有没有技能库”,而是技能库的使用时机:前者每次推理都要读,后者只作为训练支架。
本文要解决的目标非常具体:能否把结构化的 agent skills 内化到模型参数里,使 agent 在 zero-shot / no-skill inference 设置下仍能完成 ALFWorld、Search-QA、WebShop 这类多步任务。这个问题值得研究,是因为一旦 internalization 成立,agent 可以同时获得 skill prompting 的探索/归纳偏置和无技能推理的低 token 成本,避免部署时维护检索器、压缩器和 prompt 拼接链路。
2. Idea (核心思想)
SKILL0 的核心洞察是:不要把技能永远当作 inference-time prompt,而要把技能当作 training-time scaffold。训练早期给模型完整或较多技能上下文,帮助它看到“正确的多步操作模式”;训练中期用 on-policy validation 衡量每个技能对当前策略还是否有帮助;训练后期把帮助已经变弱或预算外的技能撤掉,迫使策略把行为模式固化到参数中。
与 SkillRL 这类 skill-augmented agent 相比,SKILL0 的根本差异在于目标函数和评估协议都指向“无技能推理”:SkillRL 仍依赖 explicit skills at inference,SKILL0 则在训练中有意识地制造从 with skill 到 without skill 的 curriculum shift。与普通 GRPO / AgentOCR 相比,SKILL0 不是从零探索多步行为,而是先用技能上下文提供高质量策略先验,再通过动态 curriculum 控制撤除节奏。
Figure 2 解读:SKILL0 由三块组成:a) 离线把 SkillBank 中的技能按任务相关性分组;b) 在 agent loop 中把历史、任务和 active skills 渲染成视觉上下文,让 VLM 策略产生 action 与 compression decision;c) 训练期间根据 skill helpfulness 动态选择 active skill set,并线性减少 skill budget,最终到 。
3. Method (方法)
3.1 Overall framework:把技能从 prompt scaffold 变成参数能力
整体训练流程可以理解为“先扶着走,再逐步放手”。给定初始策略 、训练数据 、SkillBank 和验证子任务 ,SKILL0 在每个 curriculum stage 中维护一个 active skill subset 。agent 每一步不是只看文本 history,而是把历史 、active skills 和压缩/高亮信息编码成视觉上下文: 策略从任务指令 和视觉上下文中同时采样动作与压缩控制: 直觉上,视觉上下文压缩承担了两个角色:一方面,它避免把完整长历史以文本形式不断塞入 prompt;另一方面,它把“技能指导 + 交互轨迹”变成模型能直接感知的 compact observation,使 RL 更新能把技能诱导出的动作模式写入参数。
3.2 Relevance-Driven Skill Grouping:给每个技能一个可验证的子任务
离线阶段先把 SkillBank 中的每个 skill file 与一个或多个 validation sub-task 对齐。论文定义 relevance 为“验证子任务的 domain/objective 是否与 skill file 编码的 skill category 匹配”,并从训练集里划出验证子任务集合 。这样做的目的不是提高检索准确率,而是为后续的 online helpfulness measurement 建立评估单位:每个技能至少有一个对应子任务,可以在当前策略上比较 with skill 与 without skill 的表现差。
released code 中这个结构落在 skills/<env>/skill_mapping.json 和 agent_system/environments/curriculum_skill_manager.py。CurriculumSkillManager 读取 skill_files 与 task_to_skill,再调用 load_skill_file() 把 ### SECTION_NAME ### 标记切成 section dict。get_task_to_sections() 把任务类型映射到具体 skill section,供环境 manager 在构建 prompt/visual context 时只注入相关 section。
def load_skill_sections(skill_mapping_file: str):
mapping = json.load(open(skill_mapping_file))
skill_files = {
name: os.path.join(os.path.dirname(skill_mapping_file), rel_path)
for name, rel_path in mapping["skill_files"].items()
}
all_skills = {}
for skill_name, path in skill_files.items():
all_skills[skill_name] = load_skill_file(path) # split by ### SECTION_NAME ###
task_to_sections = {}
for task_name, skill_name in mapping["task_to_skill"].items():
task_to_sections[task_name] = list(all_skills[skill_name].keys())
return all_skills, task_to_sections3.3 Agent loop and visual context:技能、历史和环境观测的统一编码
SKILL0 复用了 AgentOCR 风格的历史可视化。环境 manager 在 build_text_obs() 中根据当前任务、可执行 action、历史 memory 和 skill context 生成 observation;如果 OCR tool 开启,则调用 convert_texts_to_images() 把 memory context 渲染成 PIL images,再由 rollout loop 的 processor 变成 VLM multi-modal inputs。
关键输入包括:任务描述、当前环境观测、admissible actions、历史 action-observation 对、active skills、highlight config 和可选 compression factors。输出是两部分:一段供 chat template 使用的 text observation,以及一组视觉 history images。若移除这一步,模型要么回到高 token 的纯文本历史,要么失去把 skill/context 压缩成统一可视状态的机制。
def build_skill_augmented_observation(env, text_obs, compression_factors=None, init=False):
memory_contexts = env.memory.get_contexts() if hasattr(env, "memory") else []
trajectory_images = None
if env.ocr_tool and env.ocr_tool.is_enabled():
trajectory_images = env.ocr_tool.convert_texts_to_images(
memory_contexts,
batch_size=len(text_obs),
active_masks=env.active_masks,
compression_factor=compression_factors,
save_img=False,
enable_cache=True,
current_steps=[len(env.memory[i]) for i in range(len(text_obs))],
)
text_observations = []
for i, obs_i in enumerate(text_obs):
skill_context = env._get_skill_context(i)
template = env.template_no_his if init or env.config.env.history_length <= 0 else env.template
text_observations.append(template.format(
task_description=env.tasks[i],
current_observation=obs_i,
skill_context=skill_context,
))
return text_observations, trajectory_images3.4 In-Context Reinforcement Learning objective
ICRL 的奖励包含任务成功和压缩效率。论文用 表示轨迹是否成功,定义压缩奖励:
其中 控制任务成功与压缩效率的权衡。对每个 query ,old policy 采样 条 trajectory,组内 normalize 总奖励得到 advantage ,再优化带 KL regularization 的 clipped policy objective:
论文公式与 released code 实现差异:论文写 且 ,而 agent_system/reward_manager/episode_with_compression.py 使用 np.log(compression_factor) * compression_reward_coef,并在成功轨迹上给正向 compression reward、失败轨迹上可选负向 penalty;代码中的 compression_factor 语义更像 的压缩倍数,而不是论文文字里的 ratio。概念上两者都在奖励成功条件下的压缩,但符号/变量约定并不完全一致。
def compute_episode_reward(episode_reward, is_success, compression_factor,
compression_coef=0.01, failure_penalty_coef=0.0,
apply_compression=True):
compression_reward = 0.0
if apply_compression:
if is_success:
compression_reward = np.log(compression_factor) * compression_coef
else:
compression_reward = -np.log(compression_factor) * failure_penalty_coef
return episode_reward + compression_reward3.5 Helpfulness-Driven Dynamic Curriculum:按当前策略状态选择技能
SKILL0 把训练分成 个 stage,并线性衰减可用 skill budget:
每隔 个 training steps,trainer 会在 validation set 上跑两次:一次 use_skill=True,一次 use_skill=False。对每个任务类型计算 helpfulness:
$
\Delta_k = \text{Acc}(\pi_\theta, \mathcal{T}_k, \text{w/ }\mathcal{S}_k)
- \text{Acc}(\pi_\theta, \mathcal{T}_k, \text{w/o }\mathcal{S}_k) \Delta_k<0\Delta_kM^{(s)}M^{(s)}=0$,active skills 为空。这个机制很关键:如果一直保留所有技能,模型容易形成 prompt dependency;如果突然全撤,策略分布会剧烈偏移。线性 budget 和 on-policy helpfulness 共同控制撤除速度。
Figure 6 解读:不同 sub-task 的 呈现 rise-then-fall:早期技能显著有用,因为策略还未学会任务结构;中期 helpfulness 上升,说明技能正在引导策略发现有效行为;后期下降,表示策略即使无技能也能完成任务,skill dependency 被弱化。
def update_active_skills(delta_success_rates, task_to_skill, all_skills,
max_set, always_keep_general=True):
skill_deltas = defaultdict(list)
for metric_key, delta in delta_success_rates.items():
if metric_key == "success_rate" or "success_rate" not in metric_key:
continue
task = metric_key.replace("_success_rate", "")
skill_name = task_to_skill.get(task)
if skill_name is not None:
skill_deltas[skill_name].append(delta)
aggregated = {k: sum(v) / len(v) for k, v in skill_deltas.items()}
candidates = [(k, v) for k, v in aggregated.items()
if v >= 0 and k != "general_skills"]
candidates.sort(key=lambda item: -item[1])
if max_set <= 0:
active_names = []
else:
active_names = ["general_skills"] if always_keep_general else []
active_names += [name for name, _ in candidates[:max_set - len(active_names)]]
return merge_skill_sections(all_skills, active_names), active_namesverl/trainer/ppo/ray_trainer.py 中的 _validate() 与论文算法一致:先 _validate_once(use_skill=True),再 _validate_once(use_skill=False),计算 success_with - success_wo,调用 curriculum_manager.get_current_max_set(self.global_steps) 与 update_skill_set(),最后把新技能集注入 train / val / test envs。
def curriculum_validation_round(trainer):
metrics, success_with = trainer._validate_once(use_skill=True)
trainer.val_envs.set_use_skill(False)
_, success_without = trainer._validate_once(use_skill=False, skip_generation_logging=True)
trainer.val_envs.set_use_skill(True)
delta = {k: success_with.get(k, 0.0) - success_without.get(k, 0.0)
for k in set(success_with) | set(success_without)}
max_set = trainer.curriculum_manager.get_current_max_set(trainer.global_steps)
new_skills = trainer.curriculum_manager.update_skill_set(delta, max_set=max_set)
trainer.envs.update_skills(new_skills)
trainer.val_envs.update_skills(new_skills)
if trainer.test_envs is not None:
trainer.test_envs.update_skills(new_skills)
return metrics3.6 训练主循环伪代码
def skillzero_train(policy, ref_policy, dataloader, envs, curriculum, optimizer,
num_stages=3, validation_interval=10):
for stage in range(1, num_stages + 1):
max_set = curriculum.budget_for_stage(stage)
for step, batch in enumerate(dataloader):
if step % validation_interval == 0:
active_skills, _ = curriculum_validation_round(policy.trainer)
envs.update_skills(active_skills)
trajectories = rollout_group(policy, envs, batch, num_rollouts=8)
rewards = [compute_episode_reward(t.task_reward, t.success, t.compression_factor)
for t in trajectories]
advantages = normalize_groupwise(rewards)
loss = clipped_policy_loss(policy, ref_policy, trajectories, advantages)
optimizer.zero_grad()
loss.backward()
optimizer.step()
return policy3.7 Code-to-paper mapping
Code reference:
main@ee4a441a(2026-05-20) — pseudocode and mapping based on this commit
| Paper Concept | Source File | Key Class/Function |
|---|---|---|
| Skill file parsing and section extraction | agent_system/environments/env_manager.py | load_skill_file() |
| Skill context injection into Search/ALFWorld prompts | agent_system/environments/env_manager.py | SearchEnvironmentManager._get_skill_context(), AlfWorldEnvironmentManager._get_skill_context() |
| Visual context / OCR history rendering | agent_system/environments/env_manager.py, agent_system/multi_turn_rollout/utils.py | build_text_obs(), process_image() |
| Dynamic skill budget and skill selection | agent_system/environments/curriculum_skill_manager.py | CurriculumSkillManager.get_current_max_set(), update_skill_set() |
| With-skill / without-skill validation and curriculum update | verl/trainer/ppo/ray_trainer.py | _validate_once(), _validate() |
| Episode reward and compression-aware reward | agent_system/reward_manager/episode.py, agent_system/reward_manager/episode_with_compression.py | EpisodeRewardManager, EpisodeRewardManager_Compression |
| ALFWorld SkillZero launch config | scripts/train_alfworld_skillzero_3b.sh, scripts/train_alfworld_skillzero_7b.sh | env.curriculum_learning.max_set_schedule=[6,3,0], trainer.total_training_steps=180 |
| Search-QA SkillZero launch config | scripts/train_search_skillzero_3b.sh, scripts/train_search_skillzero_7b.sh | env.curriculum_learning.max_set_schedule=[5,3,0], trainer.total_training_steps=180 |
论文公式与 released code 实现差异:paper reports WebShop results for SKILL0, but this commit has no scripts/train_webshop_skillzero_3b.sh / scripts/train_webshop_skillzero_7b.sh; the available examples/gigpo_dynamic_trainer/run_webshop.sh does not set env.curriculum_learning.*. Therefore ALFWorld/Search-QA curriculum configs are reproducible from released scripts, while exact WebShop SKILL0 curriculum launch details are not fully exposed in the public repo snapshot.
4. Experimental Setup (实验设置)
4.1 Benchmarks and datasets
- ALFWorld:文本 embodied game,与 ALFRED benchmark 对齐;报告 Pick、Look、Clean、Heat、Cool、Pick2 六类任务的 success rate。论文采用 GiGPO 的训练 split;训练时每 batch 采样 16 tasks,每个 prompt 8 rollouts。论文没有给出完整训练集总样本数。
- Search-QA:多数据集检索问答,包含 NQ、TriviaQA、PopQA、HotpotQA、2Wiki、MuSiQue、Bamboogle;训练数据来自 NQ 和 HotpotQA,因此 NQ/HotpotQA 是 in-domain,其余是 out-of-domain;使用 E5 retriever。训练时每 batch 128 tasks,最大 prompt length 4,096。
- WebShop:真实网页购物式交互环境;训练选择 1,000 tasks,validation 使用 128 fixed tasks;每 batch 16 tasks,每 prompt 8 rollouts,最大 prompt length 4,096。
- Curriculum validation subset:论文设置 validation subset size 为 1,000,curriculum stages ,SkillBank 从 SkillRL 初始化。
4.2 Baselines and metrics
Baselines 覆盖三类:普通 prompting / skill prompting(Zero-Shot、Few-Shot、SkillRL)、RL methods(GRPO、AgentOCR、EvolveR、RLOO)以及 appendix 中的 memory-augmented / closed-source / search-agent baselines(ReAct、Reflexion、Mem0、ExpeL、MemP、SimpleMem、MemRL、GPT-4o、Gemini-2.5-Pro、Search-o1、Search-R1、ZeroSearch、O-Searcher、ParallelSearch、StepSearch)。
Metrics:ALFWorld 和 Search-QA 主要报告 success / accuracy (%) 以及 average context token cost (k) per step;WebShop 报告 Score (%)、Accuracy (%) 和 Tokens (k)。非显然指标中,WebShop Score 是购物任务匹配程度的连续评分,Accuracy 是是否成功完成购买/匹配目标商品的离散成功率。
4.3 Training config from paper and released scripts
论文声明:Qwen2.5-VL 系列最多训练 180 steps,硬件为 4 H800 GPUs。released code 的实际 launch scripts 与之对应:
ALFWorld SkillZero
- Config paths:
scripts/train_alfworld_skillzero_3b.sh,scripts/train_alfworld_skillzero_7b.sh - Models:
Qwen/Qwen2.5-VL-3B-Instruct,Qwen/Qwen2.5-VL-7B-Instruct - Batch / rollout:
train_data_size=16,val_data_size=128,group_size=8,env.rollout.n=8 - Lengths:
data.max_prompt_length=3072,data.max_response_length=512,env.max_steps=50 - Optimization:
algorithm.adv_estimator=grpo,actor_rollout_ref.actor.optim.lr=1e-6,ppo_mini_batch_size=256,ppo_micro_batch_size_per_gpu=8,actor.use_kl_loss=False - Curriculum:
env.curriculum_learning.enable=True,max_set_schedule=[6,3,0],trainer.test_freq=10,trainer.total_training_steps=180 - Hardware in script:
trainer.n_gpus_per_node=4,trainer.nnodes=1
Search-QA SkillZero
- Config paths:
scripts/train_search_skillzero_3b.sh,scripts/train_search_skillzero_7b.sh - Models:
Qwen/Qwen2.5-VL-3B-Instruct,Qwen/Qwen2.5-VL-7B-Instruct - Batch / rollout:
train_data_size=128,val_data_size=512,group_size=8,env.rollout.n=8 - Lengths:
data.max_prompt_length=4096,data.max_response_length=512,env.max_steps=4 - Optimization:
algorithm.adv_estimator=grpo,actor_rollout_ref.actor.optim.lr=1e-6,ppo_mini_batch_size=512,ppo_micro_batch_size_per_gpu=16,actor.use_kl_loss=False - Curriculum:
env.curriculum_learning.enable=True,max_set_schedule=[5,3,0],trainer.test_freq=10,trainer.total_training_steps=180 - Hardware in script:
trainer.n_gpus_per_node=4,trainer.nnodes=1
WebShop 的 paper-level setup 如上,但 public repo snapshot 没有同名 SkillZero curriculum launch script;因此 WebShop 的 exact released training override 无法像 ALFWorld/Search-QA 一样逐项核对。
5. Experimental Results (实验结果)
5.1 Main results: ALFWorld and Search-QA
Table 1 的核心结论是:SKILL0 在无技能推理时显著优于普通 RL baseline,并且 token cost 很低。
| Model | Method | ALFWorld Avg / Cost | Search-QA Avg / Cost | Notes |
|---|---|---|---|---|
| Qwen2.5-(VL)-3B | GRPO | 79.9 / 1.02k | 36.4 / 0.61k | standard RL baseline |
| Qwen2.5-(VL)-3B | AgentOCR | 78.2 / 0.38k | 34.2 / 0.26k | visual context, no skill |
| Qwen2.5-(VL)-3B | SkillRL† | 82.4 / 2.21k | 38.9 / 0.87k | validated with skill augmentation |
| Qwen2.5-(VL)-3B | SKILL0 | 87.9 / 0.38k | 40.8 / 0.18k | skill-free inference |
| Qwen2.5-(VL)-7B | GRPO | 81.8 / 0.95k | 41.9 / 0.73k | standard RL baseline |
| Qwen2.5-(VL)-7B | AgentOCR | 81.2 / 0.43k | 40.1 / 0.36k | visual context, no skill |
| Qwen2.5-(VL)-7B | SkillRL† | 89.9 / — | 47.1 / — | uses skill augmentation |
| Qwen2.5-(VL)-7B | SKILL0 | 89.8 / 0.41k | 44.4 / 0.34k | skill-free inference |
更细的 ALFWorld per-task numbers:3B SKILL0 在 Pick/Look/Clean/Heat/Cool/Pick2 上分别为 95.6 / 80.4 / 100 / 86.7 / 78.7 / 75.2,Avg 87.9;7B SKILL0 分别为 100 / 85.8 / 94.6 / 81.9 / 85.7 / 80.1,Avg 89.8。Search-QA 3B SKILL0 在 NQ/TriviaQA/PopQA/HotpotQA/2Wiki/MuSiQue/Bamboogle 上为 39.8 / 57.5 / 42.3 / 35.1 / 33.7 / 13.3 / 63.7,Avg 40.8;7B 为 42.7 / 61.1 / 45.3 / 40.0 / 38.3 / 16.4 / 66.9,Avg 44.4。
5.2 Main results: WebShop
Table 2 显示 WebShop 上技能内化带来的收益更直接:无技能 SKILL0 在 7B 下达到 85.1 Score / 74.2 Accuracy,同时 token cost 只有 0.46k。
| Method | w/ Skills | 3B Score / Acc / Tokens | 7B Score / Acc / Tokens |
|---|---|---|---|
| Zero-Shot | No | 23.4 / 6.3 / 0.46k | 26.8 / 7.8 / 0.48k |
| Few-Shot | Yes | 45.8 / 18.4 / 0.78k | 51.2 / 24.2 / 0.91k |
| AgentOCR | No | 75.2 / 56.3 / 0.42k | 78.6 / 59.3 / 0.40k |
| SKILL0 | Yes | 80.9 / 64.1 / 0.94k | 85.3 / 71.9 / 0.89k |
| SKILL0 | No | 78.6 / 66.4 / 0.49k | 85.1 / 74.2 / 0.46k |
5.3 Training dynamics
Figure 3 解读:在 Qwen2.5-VL-3B 上,SKILL0 的训练曲线相较 AgentOCR 更稳定地上升;这支持论文的解释:skill curriculum 不是仅在 prompt 中提供即时帮助,而是在训练过程中逐渐改变策略本身。
Figure 4 解读:7B 模型上同样能看到 SKILL0 与 AgentOCR 的差距。更大的 base model 并没有消除 curriculum 的作用,说明 skill internalization 不是小模型补丁,而是对 agentic RL 训练路径的改变。
Figure 5 解读:a) with-skill validation 早期上升更快;without-skill validation 初始更低但后期追上,呈现 internalization 趋势。b) 在严格无技能推理下,SKILL0 仍优于 AgentOCR。c) 与 GRPO/SkillRL 的无技能曲线相比,SKILL0 后期仍在提升,说明动态撤掉技能没有导致能力坍塌。
Figure 9 解读:ALFWorld 的 subtask dynamics 表明不同任务类型的学习速度不一致;Pick / Clean 等技能更容易形成稳定提升,而 Pick2 这类组合任务仍更难,说明 skill internalization 对复杂组合行为仍受任务结构影响。
Figure 10 解读:Search-QA 的分技能类别曲线显示,in-domain 与 out-of-domain QA 子任务均从 curriculum 中受益,但不同数据集的最终上限不同;这与论文的设置一致:NQ/HotpotQA 是训练来源,其余数据集更考验泛化。
5.4 Ablations

Figure 7 解读:skill budget 不是越大越好。始终保留所有技能会保持 prompt dependency;直接 则失去训练早期的技能支架。论文主设置的递减 budget 在“引导学习”和“撤掉依赖”之间更平衡。
Figure 8 解读:不同 skill budget schedule 在训练过程中的曲线差异说明,internalization 不是最终一步切换造成的,而是整个训练过程中 skill availability 的轨迹影响了策略收敛路径。
Table 5 的详细 ablation 给出更清楚的数值:完整 SKILL0 在 ALFWorld 无技能评估为 87.9;固定 [6,6,6] 的无技能结果降到 72.6(-15.3),说明一直依赖技能会伤害无技能泛化;较细的 [6,4,2,1,0] schedule 为 71.1(-16.8),说明阶段过多/撤除路径不一定更好;直接 [0,0,0] 为 78.9(-9.0),说明完全不用技能训练会少掉早期支架。
动态课程中的 Filter / Rank / Select 三步都影响结果。论文表中完整 Filter & Rank & Select 为 with-skill 86.3、without-skill 87.9;去掉 Filter 后变为 81.6 / 78.9;去掉 Rank、改随机选择后变为 76.6 / 62.9,说明 helpfulness 排序是最关键的组件之一。
Validation interval 的 ablation: 时 ALFWorld / Search-QA 为 87.9 / 48.9; 为 87.5 / 49.6; 降到 78.1 / 42.3。过低 interval 会增加评估开销但收益有限,过高 interval 会让技能选择滞后于策略状态。
5.5 More comparisons and limitations
Appendix 的更广泛比较显示:ALFWorld 上,3B SKILL0 Avg 87.9、7B SKILL0 Avg 89.8,超过 GPT-4o 48.0、Gemini-2.5-Pro 60.3,以及 ExpeL 46.3、SimpleMem 62.5、Mem0 54.7、MemRL 21.4 等 memory-augmented 方法。Search-QA 上,SKILL0 3B / 7B Avg 为 40.8 / 44.4;skill-augmented SkillRL† 在部分设置仍有更高数值(如 7B Avg 47.1),但它不是无技能推理协议。
论文没有单独的 limitations section;从实验和代码边界看,主要限制有四点。第一,方法依赖已有 SkillBank,并需要能把技能映射到验证子任务;如果任务没有可分解的 skill categories,helpfulness 估计会困难。第二,curriculum 每次验证要跑 with-skill / without-skill 两套评估,训练开销高于普通 GRPO。第三,实验集中在 ALFWorld、Search-QA、WebShop,尚未证明在更开放的长程软件工程或真实网页环境中同样稳定。第四,public code 对 ALFWorld/Search-QA 的 curriculum launch 支持较完整,但 WebShop 的 exact SkillZero curriculum script 在当前 commit 中缺失,复现实验需要额外询问作者或补齐配置。