ARTICLE · INTELLIGENCE

战地情报 · 详情页

来自尧图项目组的一线实战观察与深度解析

ML-For-Beginners 强化学习实战:用 Q-Learning 训练 OpenAI Gym 中的 Mountain Car 小车

ML-For-Beginners 强化学习实战:用 Q-Learning 训练 OpenAI Gym 中的 Mountain Car 小车 ML-For-Beginners 强化学习实战用 Q-Learning 训练 OpenAI Gym 中的 Mountain Car 小车【免费下载链接】ML-For-Beginners12 weeks, 26 lessons, 52 quizzes, classic Machine Learning for all项目地址: https://gitcode.com/GitHub_Trending/ml/ML-For-Beginners本文基于 ML-For-Beginners 课程第 8 周《2-Gym》一课的课后作业assignment.es.md西班牙文版与英文版 assignment.md 内容一致讲解如何将上一节CartPole 摆杆中写好的 Q-Learning 算法以最小改动迁移到 OpenAI Gym 的 Mountain Car山地车环境中并给出环境规格、状态离散化、Q 表结构与超参数调优的完整实操方案。读完本文你能掌握同一套强化学习代码适配不同 Gym 环境的方法论并知道如何针对 Mountain Car 的负奖励机制调整训练与评估策略。为什么 Mountain Car 适合做迁移练习Gym 的统一 APIOpenAI Gym 的设计目标是让所有环境提供同一套 API——即相同的reset、step、render方法以及相同的action space动作空间与observation space观测空间抽象。这意味着只要把环境替换掉、把状态离散化函数改好之前为 CartPole 写的 Q-Learning 训练代码几乎可以原样复用这正是本作业要验证的核心命题。Mountain Car 环境里有一辆被困在山谷中的小车。与 CartPole 的活越久越好不同它有一个明确的目标冲出山谷、抓住山顶的旗子。这是 Q-Learning 训练中一个很有代表性的坑——奖励函数几乎全为负值每一步 -1而成功时只给 0算法必须学会少走路才能最大化累积奖励。Mountain Car 环境规格在动手改代码之前先把环境的三个要素动作、观测、奖励完整过一遍。动作空间三选一每步只能执行以下动作之一取值含义0向左加速1不加速滑行2向右加速问题的主要诀窍小车引擎的动力不足以一次冲上山顶。因此唯一可行的策略是先向左倒车积累势能再向右冲如此往复荡动以积攒动量momentum直到速度足够大一次性冲过旗子位置。从 Q-Learning 的视角看这意味着策略必须包含远离目标的反向动作——这正是探索exploration价值的典型案例如果 ε-greedy 中的随机探索比例太低小车很容易卡在只会原地摆荡的次优策略里。观测空间只有两个连续值编号观测项最小值最大值0小车位置 (Position)-1.20.61小车速度 (Velocity)-0.070.07注意与 CartPole 的区别CartPole 的观测是 4 维小车位置、小车速度、摆杆角度、摆杆角速度而 Mountain Car 只有 2 维。但速度上限 0.07 是一个极窄的区间离散化时需要更细的粒度后面会给出具体步长参考。奖励与终止条件Mountain Car 的奖励体系颇具迷惑性当代理到达旗子位置position 0.5时奖励为0当代理位置小于 0.5 时奖励为-1即绝大多数步骤都是惩罚。一个回合episode在以下任一条件满足时结束小车位置超过 0.5成功冲顶回合步数超过 200 步超时失败。由此可以推导出一条重要的评估准则成功冲顶的回合累积奖励 -步数 - 1失败的回合累积奖励恒为 -200。因此平均累积奖励越接近 0说明策略越接近用最少步数冲顶这是后续调参时的核心观测指标。实操指令如何把 CartPole 算法改造成 Mountain Car 版本原作业的指令assignment.es.md要求从现有 notebook.ipynb 出发替换环境、修改状态离散化函数让既有算法以最小代码改动完成训练并通过调整超参数优化结果。作业同时提示很可能需要调整超参数才能让算法收敛——这一点对 Mountain Car 尤其成立。以下结合主课文README.md与官方解答solution/notebook.ipynb中的既有实现给出完整迁移方案。第 1 步替换环境把gym.make(CartPole-v1)换成import gym env gym.make(MountainCar-v0) print(env.action_space) # Discrete(3) print(env.observation_space) # Box(2,) env.reset()从源码结构看CartPole 的env.action_space.n是 2而 Mountain Car 是 3所以所有写死动作数的地方如actions (0,1)都要同步改成(0, 1, 2)。第 2 步改写状态离散化函数CartPole 版本用的是除以步长再取整的线性离散化README.md code block 6def discretize(x): return tuple((x/np.array([0.25, 0.25, 0.01, 0.1])).astype(np.int))Mountain Car 只有 2 个观测值需要按各自区间重新选步长。位置区间约 1.8-1.2 ~ 0.6速度区间仅 0.14-0.07 ~ 0.07。一个可复用的写法def discretize(x): # x[0] 位置x[1] 速度按经验取步长 return (int((x[0] 1.2) / 0.02), # 位置约 90 个离散值 int((x[1] 0.07) / 0.004)) # 速度约 35 个离散值选步长的权衡这一点主课文用 bins 离散化做了对照说明bin 越细状态空间越大上例约 90×35 ≈ 3150 个状态乘以 3 个动作共约 9450 个 Q 表条目Q 表收敛更慢但策略更精细bin 越粗学习更快但可能因速度分辨不足而冲不过旗子。主课文还提供了另一种基于np.digitize的分箱方法create_binsdiscretize_binscode block 7它对状态空间的规模有精确控制Mountain Car 中观测值本身有明确上下界0.6 / 0.07用分箱法甚至比线性取整法更合适def create_bins(i, num): return np.arange(num1)*(i[1]-i[0])/numi[0] ints [(-1.2, 0.6), (-0.07, 0.07)] # 两个观测项的取值区间 nbins [20, 20] # 各取 20 个 bin bins [create_bins(ints[i], nbins[i]) for i in range(2)] def discretize_bins(x): return tuple(np.digitize(x[i], bins[i]) for i in range(2))两种写法任选其一即可状态空间规模在 20×20 级别时训练速度明显更友好可作为起点。第 3 步保持 Q 表字典结构不变因为离散化后的状态维度未必有界主课文选择用字典而非张量存 Q 表code block 9。这部分无需任何修改只需把动作元组从 2 个扩到 3 个Q {} actions (0, 1, 2) # 从 (0,1) 改为本环境的 3 个动作 def qvalues(state): return [Q.get((state, a), 0) for a in actions]第 4 步训练主循环基本不动主课文的训练核心code block 11包括 softmax 化的动作采样probs()、ε-greedy 选择、Q 值更新、周期性打印平均累积奖励、以及保存最优 Q 表Qbest的逻辑。迁移到 Mountain Car 时主循环代码本身可以原样保留def probs(v, eps1e-4): v v - v.min() eps v v / v.sum() return v Qmax 0 cum_rewards [] rewards [] for epoch in range(100000): obs env.reset() done False cum_reward 0 while not done: s discretize(obs) if random.random() epsilon: # 利用按 Q 表 softmax 概率采样动作 v probs(np.array(qvalues(s))) a random.choices(actions, weightsv)[0] else: # 探索随机动作 a np.random.randint(env.action_space.n) obs, rew, done, info env.step(a) cum_reward rew ns discretize(obs) Q[(s, a)] (1 - alpha) * Q.get((s, a), 0) alpha * (rew gamma * max(qvalues(ns))) cum_rewards.append(cum_reward) rewards.append(cum_reward) if epoch % 5000 0: print(f{epoch}: {np.average(cum_rewards)}, alpha{alpha}, epsilon{epsilon}) if np.average(cum_rewards) Qmax: Qmax np.average(cum_rewards) Qbest Q cum_rewards []这里有两处需要结合 Mountain Car 的特点理解主循环中np.random.randint(env.action_space.n)自动适配 3 个动作无需改动Mountain Car 的最大回合长度是 200 步每 5000 个 epoch 的窗口内累积奖励的平均值会落在-200全失败到约 -100 出头成功且步数较少之间打印的平均值从 -200 向上爬升即代表在进步——这与 CartPole 中奖励向 195 逼近的向上直觉方向相反但同样是单调改善信号。第 5 步超参数调优作业明确提示的必需环节CartPole 的初始超参数为alpha 0.3、gamma 0.9、epsilon 0.90。迁移到 Mountain Car 时建议关注epsilon探索比例Mountain Car 需要反直觉的倒车动作初期可维持较高的 ε0.9 甚至更高让 Q 表覆盖到反向动作的状态随训练推进再缓慢衰减避免策略过早收敛到原地摆荡gamma折扣因子因为成功前的每一步都是 -1累积奖励在 200 步尺度内gamma在 0.9~0.99 之间都可尝试——gamma 越小越只看眼前越大越重视长期冲顶收益alpha学习率CartPole 中取 0.3Mountain Car 状态更稀疏可适当下调或训练中逐步衰减防止已学到的荡动模式被新样本冲掉主课文Reward starts to drop一节描述的正是这一现象Qbest机制就是为此保留最优快照的。评估与可视化环节code block 12/13同样可复用def running_average(x, window): return np.convolve(x, np.ones(window)/window, modevalid) plt.plot(running_average(rewards, 100))以及按 Q 表概率采样的评估回路把actions换成 3 元素、discretize换成 Mountain Car 版本后原样运行obs env.reset() done False while not done: s discretize(obs) env.render() v probs(np.array(qvalues(s))) a random.choices(actions, weightsv)[0] obs, _, done, _ env.step(a) env.close()官方解答 notebooksolution/notebook.ipynb中额外演示了用env.render(modergb_array)逐帧截图、再用 PIL 拼成 GIF 的完整评估流程迁移到 Mountain Car 时这段代码同样适用可以直观看到小车左冲右荡、越荡越高的学成轨迹。评分标准Rubric原作业给出三档评分标准迁移时可以作为自检清单等级标准优秀Exemplary将 Q-Learning 算法从 CartPole 示例成功迁移代码改动极小且能在200 步以内抓住旗子解决该问题合格Adequate从网上采用了新的 Q-Learning 实现但文档完善或采用了既有算法但未能达到期望结果待改进Needs Improvement未能成功迁移任何算法但已有实质性进展如实现了状态离散化、Q 表数据结构等200 步以内这一门槛与环境本身的最大回合长度200 步一致只要成功冲顶天然就落在 200 步以内因此该标准的实质是策略要真正学会冲顶而不是摆荡到超时。小结本作业的教学价值在于完整走了一遍环境迁移的最小改动路径换gym.make环境名 → 重写 2 维discretize→ 动作元组扩为 3 元素 → 复用字典 Q 表与训练主循环 → 按负奖励特性调 ε/γ/α 并盯住平均累积奖励。 Mountain Car 相对 CartPole 多出的难点——稀疏且全负的奖励、必须依赖反向探索才能学到的动量策略、速度观测区间的细粒度离散——使它成为检验算法可移植性与超参数敏感度的绝佳沙盒。完成本课后课程会进一步引入动作空间也为连续、观测更复杂如 Atari 像素的场景那将需要神经网络等更强的函数逼近手段。【免费下载链接】ML-For-Beginners12 weeks, 26 lessons, 52 quizzes, classic Machine Learning for all项目地址: https://gitcode.com/GitHub_Trending/ml/ML-For-Beginners创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
RELATED READING

延伸阅读

更多一线实战笔记与深度复盘,助您持续精进