FEATURED · 精选文章

GRPO强化学习算法:多语言与非英语环境下的高效优化实战

发布时间 / 2026/8/20 4:41:19
来源 / 创域科博编辑部
栏目 / 资讯中心
GRPO强化学习算法:多语言与非英语环境下的高效优化实战 大家好我是专注于技术实战分享的博主。在探索前沿AI技术时我们常常发现许多优秀的算法和模型研究都集中在英语语境下这给非英语场景的应用带来了不小的挑战。近期一种名为GRPO的强化学习优化方法在多语言领域取得了突破性进展它如何超越英语的局限在中文、日语、代码等多样化的非英语环境中实现高效训练成为了许多开发者和研究者关注的焦点。本文将为你系统拆解GRPO的核心原理并提供一套从理论到实践、从环境配置到代码实现的完整指南无论你是刚接触强化学习的新手还是希望将先进算法应用于具体业务场景的工程师都能从中获得可直接复用的经验。1. GRPO 核心概念超越英语局限的强化学习新范式在深入代码之前我们首先要理解GRPO是什么以及它为何在多语言场景中显得尤为重要。1.1 什么是GRPOGRPO即Group Relative Policy Optimization中文可译为“组相对策略优化”。它是一种新兴的强化学习算法属于策略梯度方法家族。与大家熟悉的PPO近端策略优化相比GRPO的核心创新在于其优化目标。传统PPO算法通过限制新旧策略之间的差异通过KL散度或裁剪来稳定训练其优化目标通常基于绝对的优势函数估计。而GRPO则引入了一个“组”的概念在组内对策略进行相对比较和优化。简单来说它不再追求策略的绝对好坏而是关注一个策略相对于同一批次组内其他策略的表现排名。这种相对比较的机制使其对奖励函数的尺度不那么敏感这在奖励信号稀疏、难以设计或存在偏差的多语言、非结构化任务中展现出了更强的鲁棒性。1.2 为什么GRPO特别适合多语言与非英语环境多语言和非英语环境下的AI模型训练面临几个独特挑战而GRPO的设计恰好能应对这些挑战奖励稀疏与难以量化在文本生成、翻译或代码生成任务中如何为一句中文回复或一段Python代码设计一个精确、平滑的奖励函数非常困难。GRPO的相对比较特性降低了对精确奖励值的依赖只需能区分组内样本的优劣即可。数据分布差异大不同语言的语法、词序、文化语境差异巨大。GRPO的组内优化可以更灵活地适应不同数据分布避免模型过度拟合某一种语言模式。缓解奖励黑客Reward Hacking模型可能会学会利用奖励函数的漏洞生成高分但无意义的输出。相对比较能在一定程度上抑制这种“钻空子”的行为因为模型需要持续优于同组其他候选而不是单纯刷高某个绝对分数。对齐人类偏好在大语言模型LLM的微调中GRPO可以与人类反馈强化学习RLHF结合用于偏好对齐。在多语言场景下收集高质量的人类偏好数据成本高昂GRPO能更高效地利用有限的偏好对比数据。2. 环境准备与核心工具在开始实战之前我们需要搭建一个可以进行GRPO实验的环境。本文将基于PyTorch框架和一个简化的自定义环境进行演示确保代码清晰可复现。2.1 基础环境配置首先确保你的Python环境在3.8以上。我们使用conda或venv创建独立的虚拟环境。# 创建并激活虚拟环境 (以conda为例) conda create -n grpo_demo python3.9 conda activate grpo_demo # 安装核心依赖 pip install torch1.9.0 --index-url https://download.pytorch.org/whl/cpu # 根据你的CUDA版本选择 pip install numpy pandas matplotlib tqdm pip install transformers # 用于处理文本/语言模型 pip install datasets # 用于加载数据集可选用于更复杂的数据处理版本说明本文示例代码基于PyTorch 1.13.0和Transformers 4.30.0编写。不同版本间API可能略有差异如果遇到问题请检查相应库的官方文档。核心逻辑是通用的。2.2 项目结构规划一个清晰的项目结构有助于管理代码。建议创建如下目录grpo_multilingual_demo/ ├── config/ # 配置文件 │ └── default.yaml ├── data/ # 存放数据 │ └── sample_multilingual_prompts.jsonl ├── src/ # 源代码 │ ├── __init__.py │ ├── environment.py # 自定义强化学习环境 │ ├── grpo.py # GRPO算法核心实现 │ ├── model.py # 策略网络和价值网络定义 │ └── train.py # 主训练脚本 ├── outputs/ # 训练输出如模型、日志 └── requirements.txt在项目根目录下创建requirements.txt文件记录依赖torch1.9.0 numpy1.21.0 transformers4.25.0 tqdm4.64.0 pyyaml6.0 # 用于读取yaml配置3. GRPO 算法原理与实现拆解理解原理是灵活应用的前提。本节我们将深入GRPO的数学基础并用代码实现其核心组件。3.1 算法核心组相对优势估计GRPO的关键在于其损失函数。假设我们有一组大小为N的轨迹样本例如针对同一个提示词模型生成的N个不同回复。对于组内的每个样本i我们计算其优势函数A_i。在GRPO中我们使用组内的相对优势。一种常见的实现方式是使用Bradley-Terry 模型或Plackett-Luce 模型来建模偏好概率。损失函数鼓励模型生成高奖励样本的概率高于低奖励样本。简化版的GRPO策略损失可以表示为L(θ) - E [ log(σ(β * (A_i - A_j))) ]其中σ是sigmoid函数β是一个温度系数A_i和A_j是组内一对样本的优势值。这个损失函数本质上是在优化策略使得高优势样本被选中的概率远高于低优势样本。3.2 代码实现GRPO核心类下面我们在src/grpo.py中实现一个简化但完整的GRPO算法类。# 文件路径src/grpo.py import torch import torch.nn as nn import torch.nn.functional as F from torch.distributions import Categorical import numpy as np class GRPO: 简化的Group Relative Policy Optimization实现。 假设我们已有策略网络(policy_net)和价值网络(value_net)。 def __init__(self, policy_net, value_net, lr1e-4, gamma0.99, beta0.1, clip_epsilon0.2): 初始化GRPO优化器。 Args: policy_net: 策略网络输出动作概率分布。 value_net: 价值网络输出状态价值估计。 lr: 学习率。 gamma: 奖励折扣因子。 beta: 相对优势比较的温度系数。 clip_epsilon: PPO中用于裁剪策略比率的上限。 self.policy_net policy_net self.value_net value_net self.gamma gamma self.beta beta self.clip_epsilon clip_epsilon # 使用Adam优化器 self.policy_optimizer torch.optim.Adam(policy_net.parameters(), lrlr) self.value_optimizer torch.optim.Adam(value_net.parameters(), lrlr) def compute_advantages(self, rewards, values, dones): 计算广义优势估计(GAE)。 Args: rewards: 奖励序列形状 [T, batch_size] values: 价值估计序列形状 [T1, batch_size] dones: 终止标志序列形状 [T, batch_size] Returns: advantages: 优势函数序列形状 [T, batch_size] returns: 回报序列形状 [T, batch_size] T len(rewards) advantages torch.zeros_like(rewards) returns torch.zeros_like(rewards) # 简化计算实际中应使用GAE(lambda) gae 0 for t in reversed(range(T)): delta rewards[t] self.gamma * values[t1] * (1 - dones[t]) - values[t] gae delta self.gamma * gae advantages[t] gae returns[t] advantages[t] values[t] return advantages, returns def update(self, states, actions, old_log_probs, rewards, dones): 执行一次GRPO更新。 Args: states: 状态序列列表。 actions: 动作序列列表。 old_log_probs: 旧策略下动作的对数概率。 rewards: 奖励序列。 dones: 终止标志序列。 # 将数据转换为张量 states torch.stack(states) actions torch.stack(actions) old_log_probs torch.stack(old_log_probs) rewards torch.stack(rewards) dones torch.stack(dones) batch_size states.shape[1] # 假设states形状为[T, batch_size, state_dim] # 计算当前价值估计 current_values self.value_net(states).squeeze(-1) # [T, batch_size] # 为GAE计算需要最后一个状态的价值 with torch.no_grad(): # 这里简化处理实际需要最后一个next_state的价值 next_value torch.zeros(batch_size) values torch.cat([current_values, next_value.unsqueeze(0)], dim0) # 计算优势函数和回报 advantages, returns self.compute_advantages(rewards, values[:-1], dones) advantages (advantages - advantages.mean()) / (advantages.std() 1e-8) # 标准化 # --- 核心GRPO组相对损失计算 --- # 假设我们将一个batch内的所有样本视为一个“组” # 计算当前策略的对数概率 action_dists self.policy_net(states) new_log_probs action_dists.log_prob(actions) # 策略比率 ratios torch.exp(new_log_probs - old_log_probs) # 1. 基于相对优势的损失GRPO核心思想 # 我们使用一个简化的实现鼓励高优势样本有更高的策略概率 # 这里将优势函数视为“奖励”使用带裁剪的PPO风格损失但优化目标包含了相对比较的思想 # 更复杂的实现会显式地对组内样本进行两两比较 # 计算策略损失结合裁剪 surr1 ratios * advantages surr2 torch.clamp(ratios, 1 - self.clip_epsilon, 1 self.clip_epsilon) * advantages policy_loss -torch.min(surr1, surr2).mean() # 2. 价值函数损失MSE value_loss F.mse_loss(current_values, returns) # 3. 可选策略熵奖励鼓励探索 entropy_bonus action_dists.entropy().mean() # 总损失 total_loss policy_loss 0.5 * value_loss - 0.01 * entropy_bonus # 反向传播与优化 self.policy_optimizer.zero_grad() self.value_optimizer.zero_grad() total_loss.backward() # 可以添加梯度裁剪 torch.nn.utils.clip_grad_norm_(self.policy_net.parameters(), max_norm0.5) torch.nn.utils.clip_grad_norm_(self.value_net.parameters(), max_norm0.5) self.policy_optimizer.step() self.value_optimizer.step() return { total_loss: total_loss.item(), policy_loss: policy_loss.item(), value_loss: value_loss.item(), entropy: entropy_bonus.item() }代码解释compute_advantages: 计算优势函数这是评估动作好坏的关键。我们使用了简化的回报计算工业级实现通常会使用GAE(λ)来平衡偏差和方差。update: 这是GRPO更新的核心。我们首先计算当前策略的概率和优势然后通过裁剪的策略比率和优势的乘积来计算损失。虽然这个示例没有显式实现两两比较的Bradley-Terry模型但通过优势函数的标准化和策略优化已经体现了“相对优化”的思想——模型被鼓励去采取相对于平均基线更好的动作。关键点GRPO的精髓在于advantages的计算和其在损失函数中的应用。在多语言环境中rewards的设计至关重要而GRPO的相对性使其对奖励的绝对尺度不敏感。4. 实战构建多语言文本生成环境与训练现在我们将GRPO应用到一个具体的多语言场景优化一个文本生成模型使其生成更符合特定风格如“正式”、“简洁”的非英语文本。4.1 设计自定义强化学习环境我们创建一个简单的环境其状态是当前的文本上下文动作是选择下一个词奖励由一个批评者模型或规则根据生成文本的风格符合度给出。# 文件路径src/environment.py import torch from transformers import AutoTokenizer, AutoModelForSequenceClassification import numpy as np class MultilingualTextEnv: 一个简化的多语言文本生成强化学习环境。 def __init__(self, base_model_namebert-base-multilingual-cased, styleformal): Args: base_model_name: 用于编码和初始化的多语言模型。 style: 目标风格如 formal(正式), concise(简洁)。 self.tokenizer AutoTokenizer.from_pretrained(base_model_name) # 这里我们假设有一个能判断文本风格的批评者模型。 # 为简化我们用一个随机函数模拟真实场景需替换为训练好的分类器或规则。 self.critic_model None # placeholder self.style style self.max_length 50 self.current_step 0 self.current_text self.prompt # 初始提示 def reset(self, prompt): 重置环境给定一个提示词。 self.prompt prompt self.current_text prompt self.current_step 0 # 将当前文本编码为状态例如使用CLS token的嵌入 state self._text_to_state(self.current_text) return state def _text_to_state(self, text): 将文本转换为状态向量简化版使用词嵌入的平均。 inputs self.tokenizer(text, return_tensorspt, truncationTrue, max_length512) with torch.no_grad(): # 这里应该使用一个编码模型例如BERT来获取句子表示。 # 为演示我们返回一个随机向量。实际应用需替换为真实的模型前向传播。 state_vec torch.randn(768) # 假设状态维度为768 return state_vec def step(self, action_token_id): 执行一个动作生成一个词。 Args: action_token_id: 模型预测的下一个词的token id。 Returns: next_state, reward, done, info # 将action token解码为词 new_word self.tokenizer.decode([action_token_id]) self.current_text new_word.strip() self.current_step 1 # 检查是否终止 done (self.current_step self.max_length) or (action_token_id self.tokenizer.sep_token_id) # 计算奖励核心 # 在多语言场景下奖励函数需要处理不同语言。 # 示例当生成文本达到一定长度后评估其风格符合度。 reward 0.0 if done or self.current_step % 5 0: # 每5步或结束时评估一次 reward self._compute_reward(self.current_text) next_state self._text_to_state(self.current_text) info {generated_text: self.current_text} return next_state, reward, done, info def _compute_reward(self, text): 计算奖励评估生成文本与目标风格的匹配程度。 这是一个模拟函数。真实实现可能包括 1. 使用一个风格分类器模型。 2. 使用规则如句子长度、词汇复杂度。 3. 基于人类反馈的奖励模型RMB。 # 模拟一个简单的规则如果文本中包含某些“正式”词汇则给正奖励。 # 注意这只是一个极其简化的示例不具备实际判别力。 formal_keywords { en: [furthermore, however, therefore, thus], zh: [此外, 然而, 因此, 综上所述], ja: [さらに, しかし, したがって, まとめると] } # 这里需要检测文本语言为简化我们假设是中文 lang zh score 0 for kw in formal_keywords.get(lang, []): if kw in text: score 0.1 # 添加随机噪声模拟不确定性 score np.random.normal(0, 0.02) return max(0, min(1, score)) # 限制在[0,1]区间4.2 定义策略网络与价值网络我们使用简单的多层感知机MLP作为策略网络和价值网络。# 文件路径src/model.py import torch import torch.nn as nn import torch.nn.functional as F from torch.distributions import Categorical class PolicyNetwork(nn.Module): 策略网络输入状态输出动作token的概率分布。 def __init__(self, state_dim, action_dim, hidden_dim256): super().__init__() self.net nn.Sequential( nn.Linear(state_dim, hidden_dim), nn.ReLU(), nn.Linear(hidden_dim, hidden_dim), nn.ReLU(), nn.Linear(hidden_dim, action_dim) ) def forward(self, state): logits self.net(state) return Categorical(logitslogits) # 返回一个分类分布 class ValueNetwork(nn.Module): 价值网络输入状态输出状态价值标量。 def __init__(self, state_dim, hidden_dim256): super().__init__() self.net nn.Sequential( nn.Linear(state_dim, hidden_dim), nn.ReLU(), nn.Linear(hidden_dim, hidden_dim), nn.ReLU(), nn.Linear(hidden_dim, 1) ) def forward(self, state): return self.net(state)4.3 组装训练流程现在我们将环境、模型和GRPO算法组合起来编写主训练脚本。# 文件路径src/train.py import torch import numpy as np from tqdm import tqdm import yaml import os import sys sys.path.append(os.path.dirname(os.path.dirname(os.path.abspath(__file__)))) from src.environment import MultilingualTextEnv from src.model import PolicyNetwork, ValueNetwork from src.grpo import GRPO def load_config(config_pathconfig/default.yaml): with open(config_path, r, encodingutf-8) as f: config yaml.safe_load(f) return config def main(): # 加载配置 config load_config() # 初始化环境 env MultilingualTextEnv( base_model_nameconfig[env][base_model], styleconfig[env][target_style] ) # 假设动作空间是词表大小简化实际应从tokenizer获取 # 这里用一个较小的数字演示真实情况可能是数万 state_dim 768 action_dim 10000 # 示例词表大小 # 初始化策略网络和价值网络 policy_net PolicyNetwork(state_dim, action_dim, config[model][hidden_dim]) value_net ValueNetwork(state_dim, config[model][hidden_dim]) # 初始化GRPO优化器 grpo GRPO( policy_netpolicy_net, value_netvalue_net, lrconfig[training][lr], gammaconfig[training][gamma], betaconfig[training][beta], clip_epsilonconfig[training][clip_epsilon] ) # 训练循环 num_episodes config[training][num_episodes] max_steps config[env][max_length] # 示例提示词多语言 prompts [ 请解释机器学习。, # 中文 Explain machine learning., # 英文 機械学習について説明してください。 # 日文 ] for episode in tqdm(range(num_episodes), descTraining Episodes): # 随机选择一个提示词 prompt np.random.choice(prompts) state env.reset(prompt) episode_states [] episode_actions [] episode_log_probs [] episode_rewards [] episode_dones [] for step in range(max_steps): state_tensor torch.FloatTensor(state).unsqueeze(0) # [1, state_dim] # 策略网络选择动作 with torch.no_grad(): action_dist policy_net(state_tensor) action action_dist.sample() log_prob action_dist.log_prob(action) # 与环境交互 next_state, reward, done, info env.step(action.item()) # 存储轨迹 episode_states.append(state_tensor) episode_actions.append(action) episode_log_probs.append(log_prob) episode_rewards.append(reward) episode_dones.append(done) state next_state if done: break # 一个episode结束进行GRPO更新 if len(episode_rewards) 0: loss_info grpo.update( episode_states, episode_actions, episode_log_probs, torch.FloatTensor(episode_rewards), torch.FloatTensor(episode_dones) ) # 打印日志 if (episode 1) % config[logging][print_interval] 0: print(fEpisode {episode1}, Total Loss: {loss_info[total_loss]:.4f}, fAvg Reward: {np.mean(episode_rewards):.4f}, fGenerated Text: {info.get(generated_text, )[:50]}...) # 保存训练好的模型 torch.save(policy_net.state_dict(), outputs/policy_net_final.pth) torch.save(value_net.state_dict(), outputs/value_net_final.pth) print(Training completed. Models saved to outputs/.) if __name__ __main__: main()4.4 配置文件创建配置文件config/default.yaml# 环境配置 env: base_model: bert-base-multilingual-cased target_style: formal max_length: 30 # 模型配置 model: hidden_dim: 256 # 训练配置 training: num_episodes: 1000 lr: 3e-4 gamma: 0.99 beta: 0.2 clip_epsilon: 0.2 # 日志配置 logging: print_interval: 504.5 运行与验证在项目根目录下运行训练脚本python src/train.py由于我们的奖励函数是模拟的你可能会看到奖励值在某个水平附近随机波动。在真实应用中你需要用真实的风格分类器或人类反馈奖励模型替换_compute_reward函数。预期输出示例Training Episodes: 100%|██████████| 1000/1000 [05:1200:00, 3.21it/s] Episode 50, Total Loss: 0.1234, Avg Reward: 0.4500, Generated Text: 请解释机器学习。 此外 我们 可以 ... Episode 100, Total Loss: 0.0987, Avg Reward: 0.5200, Generated Text: Explain machine learning. However, it is ... ... Training completed. Models saved to outputs/.5. 多语言与非英语环境下的关键问题与解决方案将GRPO应用于多语言场景时会遇到一些独特挑战。以下是常见问题及排查思路。问题现象可能原因解决方案与排查思路奖励始终为零或极低1. 奖励函数设计不合理无法有效区分好坏输出。2. 文本编码Tokenizer不匹配导致模型无法理解输入。3. 动作空间词表过大探索困难。1.检查奖励函数先用少量样本手动计算奖励确保其能反映质量差异。对于多语言确保奖励模型或规则支持所有目标语言。2.统一Tokenizer确保环境、策略网络使用的词表一致。对于多语言使用bert-base-multilingual-cased等支持多语言的Tokenizer。3.缩小动作空间在初期可以限制在高频词或子词单元上进行训练。训练不稳定损失剧烈波动1. 优势估计方差过大。2. 学习率过高。3. 批次组内样本差异过大导致相对比较失效。1.使用GAE(λ)实现完整的GAE来估计优势平衡偏差和方差。2.调整学习率和裁剪系数降低lr微调clip_epsilon如0.1。3.优化组构建策略确保组内样本来自相似的任务或语言避免将中文和英文样本放在同一组直接比较。可以按语言或提示词类型分组。模型生成无意义或重复文本1. 探索不足陷入局部最优。2. 奖励函数存在漏洞被模型“黑客攻击”。3. 价值函数估计不准导致优势信号错误。1.增加熵奖励系数在GRPO损失中增加熵奖励项鼓励探索。2.设计更鲁棒的奖励结合多个奖励信号如流畅度、相关性、风格匹配或使用基于模型的奖励验证。3.分离价值网络训练可以多更新几次价值网络使其更准确再进行策略更新。非英语语言性能显著差于英语1. 预训练模型在多语言数据上表征能力不均衡。2. 奖励数据或偏好数据存在英语偏见。3. Tokenizer对非英语语言的划分效率低。1.使用更均衡的多语言模型考虑XLM-RoBERTa或专门在目标语言上微调过的编码器。2.收集目标语言的偏好数据这是根本解决方案。如果资源有限可以使用高质量翻译加回译back-translation来扩充数据。3.调整分词策略对于中文、日文等使用基于字的Tokenizer或SentencePiece模型可能比BPE更有效。“组”的大小如何选择组大小影响训练效率和稳定性。经验法则组大小至少为4通常8-32是一个较好的范围。太小则相对比较不可靠太大则计算开销增加且可能包含过多异质样本。可以将其设置为一个超参数进行调优。6. 工程最佳实践与进阶建议要将GRPO可靠地应用于生产级的多语言任务需要遵循以下工程实践。6.1 奖励工程多语言场景的核心奖励函数是GRPO成功的基石。在多语言环境中设计奖励需考虑多维度奖励不要只依赖单一指标。结合风格匹配度使用多语言风格分类器。流畅度使用目标语言的预训练模型计算困惑度PPL。事实一致性对于知识性任务使用检索增强或事实核查模型。安全性添加毒性或偏见检测模型作为负奖励。奖励标准化与校准不同语言、不同任务的奖励尺度可能不同。在计算组内相对优势前应对奖励进行分语言或分任务标准化使其均值和方差大致相同。人类反馈的融入对于关键任务收集少量多语言人类偏好数据训练一个奖励模型Reward Model。GRPO可以利用这个模型提供的相对偏好信号进行优化这比直接使用标量奖励更鲁棒。6.2 高效的数据与组构建策略按语言/任务分组在构建用于GRPO更新的“组”时务必保证组内样本的同质性。将中文提示的生成结果和英文提示的生成结果放在一起比较是不公平的。应在数据加载时按提示语言或类型进行分组。课程学习从简单的任务短文本生成、单一语言开始训练逐步增加难度长文本、多语言混合提示这有助于稳定训练。数据增强对于低资源语言可以使用回译、同义词替换、语法结构变换等方式增强数据提高模型的泛化能力。6.3 模型架构与初始化预训练模型初始化强烈建议使用多语言预训练模型如mT5、XLM-RoBERTa作为策略网络的骨干而不是从头训练。这提供了强大的语言理解和生成先验知识。价值网络独立价值网络应与策略网络共享底层编码器吗对于文本任务共享编码器可以节省计算但可能导致耦合过紧。一种折中方案是让价值网络拥有自己独立的轻量级头部而编码器部分与策略网络共享并冻结或微调。处理长文本GRPO需要处理整个生成序列。考虑使用Transformer解码器或RNN作为策略网络以处理可变长度的状态历史。6.4 训练稳定性技巧梯度裁剪与监控始终对策略网络和价值网络的梯度进行裁剪如max_norm0.5并监控梯度范数防止训练崩溃。学习率预热与衰减使用线性预热学习率然后根据验证集奖励进行衰减或使用余弦退火。定期评估与保存不在训练集上评估效果。保留一个多语言的验证提示集定期评估生成质量并保存验证奖励最高的模型。分布式训练对于大规模多语言任务考虑使用分布式数据并行DDP来加速样本收集即与环境交互的过程。6.5 生产环境部署考量延迟与吞吐量GRPO在推理时只需要策略网络与标准语言模型相同。关注模型量化、剪枝和ONNX导出以优化部署性能。安全与审核在部署前必须对多语言生成内容进行全面的安全性和偏见审核。GRPO优化后的模型可能学会利用奖励函数的漏洞生成看似高分但有害的内容。持续学习与监控上线后持续收集真实用户交互数据在遵守隐私政策的前提下用于定期微调奖励模型和策略模型以适应语言使用的变化。GRPO为多语言和非英语环境下的强化学习应用打开了一扇新的大门。其核心优势在于通过组内相对比较降低了对精确奖励函数的依赖从而更能适应奖励信号复杂、数据分布多样的场景。成功的应用离不开精心的奖励工程、合理的数据分组策略以及稳定的训练技巧。
RELATED — 相关阅读

相关资讯

LATEST — 最新资讯

最新发布

TODAY — 本日精选

新闻

WEEKLY — 本周精选

新闻

MONTHLY — 本月精选

新闻