简要声明
- 课程学习相关网址:
- 由于教程内容为英文,文本会进行谷歌翻译并保留部分英文专有名词,采用中文进行简要解释。
- 本学习笔记单纯是为了能对学到的内容有更深入的理解,如果有错误的地方,恳请包容和指正。
Gymnasium
Gymnasium 是一个为所有单代理强化学习环境提供 API 的项目,并包括常见环境的实现:cartpole、pendulum、mountain-car、mujoco、atari 等。
该 API 包含四个关键函数:
make
、reset
、step
和render
。 Gymnasium 的核心是Env
,一个高级 Python 类,代表强化学习理论中的马尔可夫决策过程 (MDP)。
基本用法
安装环境
pip install gymnasium[classic-control]
初始化环境
- 使用make函数初始化环境,返回一个
env
供用户交互
import gymnasium as gym
env = gym.make('CartPole-v1',render_mode="human")
与环境互动
import gymnasium as gym
env = gym.make("CartPole-v1", render_mode="human")
observation, info = env.reset() # 重置环境获得观察(observation)和信息(info)参数
for _ in range(1000):
action = env.action_space.sample() # 使用观察和信息的代理策略
# 执行动作(action)返回观察(observation)、奖励(reward)、终止(terminated)、截断(truncated)
observation, reward, terminated, truncated, info = env.step(action)
# 如果终止或者截断,则重置环境
if terminated or truncated:
observation, info = env.reset()
env.close() # 关闭环境
- 首先,使用
make
创建一个环境,并附加一个关键字“render_mode”
,指定如何可视化环境。 - 初始化环境后,
reset
环境以获得对环境的第一次观察。 - 接下来,代理在环境中执行一个动作,
step
,从而导致环境发生变化。 结果,代理从更新的环境中收到新的观察结果以及采取行动的奖励。 一种这样的动作-观察交换被称为timestep
。 - 然而,经过一些时间步长后,环境可能会结束,这称为
terminal
状态。 例如,机器人可能崩溃了,或者代理已成功完成任务,环境将需要停止,因为代理无法继续。 在gymnasium中,如果环境terminated
,则会在step
中返回。 同样,我们可能还希望环境在固定数量的时间步后结束,在这种情况下,环境会发出截断的信号。 如果terminated
或truncated
为true
,则接下来应调用reset
以重新启动环境。
Env
class gymnasium.Env
方法和属性 | 解释 |
---|---|
observation, reward, terminated, truncated, info = env.step(action) | 使用代理操作运行环境动态的一个时间步 |
observation, info = env.reset(seed, option) | 将环境重置为初始内部状态,返回初始观察结果和信息 |
env.render() | 在环境初始化期间计算由 render_mode 指定的渲染帧 |
env.action_space | 有效动作对应的Space对象,所有有效动作都应该包含在该空间中。 |
env.observation_space | 有效观测值对应的 Space 对象,所有有效观测值都应包含在该空间中。 |
env.metadata | 环境的元数据,包含渲染模式、渲染帧率等 |
env.render_mode | 初始化时确定的环境渲染模式 |
env.reward_range | 对应于代理在一个情节中的最小和最大可能奖励的元组。 默认奖励范围设置为正负无穷 |
env.EnvSpec | 通常在gymnasium.make()期间设置的环境EnvSpec |
env.close() | 用户使用完环境后,close 包含“清理”环境所需的代码。 |
env.unwarapped | 返回基本的非包装环境。 |
env.np_random | 返回环境的内部 _np_random,如果未设置,将使用随机种子进行初始化。 |
env.step()
gymnasium.Env.step(self, action: ActType) → tuple[ObsType, SupportsFloat, bool, bool, dict[str, Any]]
使用代理操作运行环境动态的一个时间步。
当一个episode结束时(终止或截断),有必要调用reset()来重置下一个episode的环境状态。
- PARAMETERS
action
(ActType) – 代理提供的用于更新环境状态的操作
- RETURNS
observation
(ObsType) – 环境观察空间的一个元素,作为代理动作的下一个观察结果reward
(SupportsFloat) – 采取行动的结果的奖励terminated
(bool) – 代理是否达到最终状态,可以是正数或负数。truncated
(bool) – 是否满足MDP范围外的截断条件。 通常,这是一个时间限制,但也可用于指示代理实际越界。 可用于在达到最终状态之前提前结束情节。info
(dict) – 包含辅助诊断信息(有助于调试、学习和记录)。
env.reset()
gymnasium.Env.reset(self, *, seed: int | None = None, options: dict[str, Any] | None = None) → tuple[ObsType, dict[str, Any]]
将环境重置为初始内部状态,返回初始观察结果和信息。
该方法通常会生成具有一定随机性的新起始状态,以确保代理探索状态空间并学习有关环境的通用策略。 这种随机性可以通过种子参数来控制,否则如果环境已经有随机数生成器并且使用seed=None调用reset(),则不会重置RNG。在初始化后立即使用种子调用,然后不再调用。
- PARAMETERS
seed
(optional int) – 用于初始化环境的 PRNG (np_random) 的种子options
(optional dict) – 用于指定如何重置环境的附加信息(可选,取决于具体环境)
- RETURNS
observation
(ObsType) – 环境观察空间的一个元素,作为代理动作的下一个观察结果info
(dict) – 包含辅助诊断信息(有助于调试、学习和记录)。
env.render()
gymnasium.Env.render(self) → RenderFrame | list[RenderFrame] | None
在环境初始化期间计算由 render_mode 指定的渲染帧。
render_mode
None
(default): 不计算渲染- “
human
”: 环境在当前显示器或终端中连续渲染,通常供人类消费。 此渲染应该在 step() 期间发生,并且不需要调用 render()。 返回无 - “
rgb_array
”: 返回表示环境当前状态的单个帧。 帧是一个 np.ndarray,形状为 (x, y, 3),表示 x×y 像素图像的 RGB 值 - “
ansi
”: 返回包含每个时间步的终端样式文本表示形式的字符串 (str) 或 StringIO.StringIO。 - “
rgb_array_list
” and “ansi_list
”: 基于列表的渲染模式版本可以通过在gymnasium.make(…, render_mode=“rgb_array_list”)期间自动应用的包装器gymnasium.wrappers.RenderCollection实现(Human除外)。 调用 render() 或 Reset() 后,收集的帧会弹出。
env.action_space
Env.action_space: spaces.Space[ActType]
有效动作对应的Space对象,所有有效动作都应该包含在该空间中。 例如,如果动作空间的类型为 Discrete 并给出值 Discrete(2),则意味着有两个有效的离散动作:0 和 1。
env.observation_space
Env.observation_space: spaces.Space[ObsType]
有效观测值对应的 Space 对象,所有有效观测值都应包含在该空间中。 例如,如果观察空间的类型为 Box 并且对象的形状为 (4,),则这表示有效的观察将是由 4 个数字组成的数组。
Register & Make
Gymnasium 允许用户自动加载环境,通过
gymnasium.make()
函数预先包装几个重要的包装器。 为此,必须事先使用gymnasium.register()
注册环境。
gymnasium.make()
gymnasium.make(id: str | EnvSpec, max_episode_steps: int | None = None, autoreset: bool | None = None, apply_api_compatibility: bool | None = None, disable_env_checker: bool | None = None, **kwargs: Any) → Env
创建先前使用gymnasium.register() 或EnvSpec 注册的环境。
- PARAMETERS
id
– 环境 ID 或 EnvSpec 的字符串。 如果使用字符串,则可以选择包含要导入的模块,例如'module:Env-v0’
。 这相当于先导入模块来注册环境,然后再创建环境max_episode_steps
– 每集的最大长度,可以覆盖注册的 EnvSpec max_episode_steps。autoreset
– 是否在每集后自动重置环境apply_api_compatibility
– 是否使用包装器包装环境,该包装器将环境步骤从完成布尔值转换为返回终止和截断布尔值。 默认情况下,参数为 None,否则优先使用此变量disable_env_checker
– 如果要添加gymnasium.wrappers.PassiveEnvChecker
,则“None”将默认为“EnvSpec
”disable_env_checker0
值,否则将使用该值kwargs
– 要传递给环境构造函数的其他参数
- RETURNS
- 应用了包装器的环境实例。
- RAISES
- Error – 如果注册表中不存在该 ID
Environments | Cart Pole为例
环境 | 安装指令 |
---|---|
Classic Control | pip install gymnasium[classic-control] |
Box2D | pip install gymnasium[box2d] |
Toy Text | pip install gymnasium[toy-text] |
MuJoCo | pip install gymnasium[mujoco] |
Atari | pip install gymnasium[atari] |
Cart Pole
import 导入 | gymnasium.make(“CartPole-v1”, render_mode=“human”) |
---|---|
Action Space 动作空间 | Discrete(2) |
Observation Space 观察空间 | Box([-4.8000002e+00 -3.4028235e+38 -4.1887903e-01 -3.4028235e+38], [4.8000002e+00 3.4028235e+38 4.1887903e-01 3.4028235e+38], (4,), float32) |
描述
一根杆子通过非驱动接头连接到小车上,小车沿着无摩擦的轨道移动。 摆锤垂直放置在小车上,目标是通过在小车上向左和向右施加力来平衡杆。
Action Space
- 该操作是一个形状为
(1,)
的ndarray
,它可以采用值{0, 1}
指示推动小车的固定力的方向。- 0: 将车推向左侧
- 1: 将车推向右侧
通过施加的力减少或增加的速度不是固定的,它取决于杆所指向的角度。 杆子的重心会改变其下方移动小车所需的能量
Observation Space
- 观察结果是一个形状为
(4,)
的ndarray
,其值对应于以下位置和速度:
Num | Observation | Min | Max |
---|---|---|---|
0 | Cart Position | -4.8 | 4.8 |
1 | Cart Velocity | -Inf | Inf |
2 | Pole Angle | ~ -0.418 rad (-24°) | ~ 0.418 rad (24°) |
3 | Pole Angular Velocity | -Inf | Inf |
虽然上述范围表示每个元素的观察空间的可能值,但它并不反映未终止情节中状态空间的允许值。
车 x 位置(索引 0)可以取 (-4.8, 4.8) 之间的值,但如果车离开 (-2.4, 2.4) 范围,则情节终止。
可以在 (-.418, .418) 弧度(或 ±24°)之间观察到极角,但如果极角不在 (-.2095, .2095)(或 ±12°)范围内,则事件终止
Rewards
由于目标是尽可能长时间地保持杆子直立,因此每采取一步(包括终止步骤)都会获得
+1
的奖励。 v1 的奖励阈值是 500,v0 的奖励阈值是 200。
Starting State
所有观测值均分配为 (-0.05, 0.05) 范围内的均匀随机值
Episode End
- 如果发生以下任何一种情况,则该剧集结束:
- 终止:极角大于±12°
- 终止:小车位置大于 ±2.4(小车中心到达显示屏边缘)
- 截断:剧集长度大于 500(v0 为 200)
import gymnasium as gym
env = gym.make("CartPole-v1", render_mode="human")
observation, info = env.reset()
for _ in range(1000):
action = env.action_space.sample()
observation, reward, terminated, truncated, info = env.step(action)
if terminated or truncated:
observation, info = env.reset()
env.close()