强化学习 1. 强化学习基础

前言

从零开始学习ai文章系列计划是个人在《动手学深度学习》和《磨菇书》两本书的学习中的个人笔记,文章也会以课本中的章节分开,即每个章节一片笔记。我会尽量的把主要内容以及遇到的难点进行记录与解决,如果哪里有错误的欢迎指正。或者不清晰的可以直接查看原文部分。

《蘑菇书》原文(课本):https://datawhalechina.github.io/easy-rl/#/

(由于有时候公式太多,可能会直接贴图片)

蘑菇书的文章结构不会跟之前《动手学深度学习》按照原文章节进行,个人会适当调节。


1. 强化学习概述

强化学习(reinforcement learning,RL)讨论的问题是智能体(agent)怎么在复杂、不确定的环境(environment)中最大化它能获得的奖励。

1.1 强化学习与监督学习

监督学习(supervised learning)假设我们有大量被标注的数据。 当神经网络做出错误的预测时,比如输入汽车的图片,它预测出来是飞机,我们就会直接告诉它,该预测是错误的,正确的标签应该是汽车。最后我们根据类似错误写出一个损失函数(loss function),通过反向传播(back propagation)来训练神经网络。通常假设样本空间中全体样本服从一个未知分布,我们获得的每个样本都是独立地从这个分布上采样获得的,即独立同分布(independent and identically distributed,简称 i.i.d.)。

强化学习中,不存在被标注的数据。我们得到的数据是相关的时间序列数据(一般根据策略采集),不满足独立同分布。另外,强化学习之所以困难,是因为智能体不能得到即时的反馈,然而我们依然希望智能体在这个环境中学习。

2. 强化学习中的术语

奖励:奖励是由环境给的一种标量的反馈信号(scalar feedback signal),这种信号可显示智能体在某一步采取某个策略的表现如何。

序列决策:在与环境的交互过程中,智能体会获得很多观测。针对每一个观测,智能体会采取一个动作,也会得到一个奖励。所以历史是状态(s)、动作(a)、奖励(r)的序列。即一系列 \((s_0,a_0,r_0),(s_1,a_1,r_1)...(s_n,a_n,r_n)\)

动作空间:在给定的环境中,有效动作的集合经常被称为动作空间(action space)。

例如:

走迷宫机器人如果只有往东、往南、往西、往北这 4 种移动方式,则其动作空间为离散动作空间

如果机器人可以向 360 度中的任意角度进行移动,则其动作空间为连续动作空间

策略 :策略是智能体的动作模型,它决定了智能体的动作。它其实是一个函数,用于把输入的状态变成动作。策略可分为两种:随机性策略 和 确定性策略。

随机性策略(stochastic policy):输入一个状态 s,输出一个概率。 这个概率是智能体所有动作的概率,然后对这个概率分布进行采样,可得到智能体将采取的动作。比如可能是有 0.7 的概率往左,0.3 的概率往右,那么通过采样就可以得到智能体将采取的动作。

确定性策略(deterministic policy)就是智能体直接采取最有可能的动作

价值函数(value function):我们用价值函数来对当前状态进行评估。价值函数用于评估智能体进入某个状态后,可以对后面的奖励带来多大的影响。价值函数值越大,说明智能体进入这个状态越有利。

3. Gym

OpenAI 的 Gym库是一个环境仿真库,里面包含很多现有的环境。针对不同的场景,我们可以选择不同的环境。

我们可以通过 pip 来安装 Gym 库,由于 Gym 库 0.26.0 及其之后的版本对之前的代码不兼容,所以我们安装 0.26.0 之前的 Gym,比如 0.25.2。

1
pip install gym==0.25.2

(我这里用的新版0.26.2,后续我的代码也都是这个版本)

1
pip install gym

此外,为了显示图形界面,我们还需要安装 pygame 库。

1
pip install pygame

由于numpy新版没有bool8这个类型,因此会报错,需要添加以下代码进行兼容(我的python12无法安装合适的旧版numpy)

1
2
if not hasattr(np, "bool8"):
np.bool8 = np.bool_

在 Python 环境中导入Gym库,如果不报错,就可以认为 Gym 库安装成功。

1
import gym

大家可以点这个链接看一看这些环境。

https://www.gymlibrary.dev/environments/classic_control/

以CartPole-v0为例

如图 1.26 所示,CartPole-v0 环境有两个动作:将小车向左移动和将小车向右移动。

我们还可以得到观测:小车当前的位置,小车当前往左、往右移的速度,杆的角度以及杆的最高点(顶端)的速度。

1
2
3
4
5
6
import gym
env = gym.make("CartPole-v1", render_mode="human")
print('观测空间 = {}'.format(env.observation_space))
print('动作空间 = {}'.format(env.action_space))
print('观测范围 = {} ~ {}'.format(env.observation_space.low, env.observation_space.high))
print('动作数 = {}'.format(env.action_space.n))

在 Gym 库中,

环境的观测空间用 env.observation_space 表示,

动作空间用 env.action_space 表示。

动作也分为离散动作和连续动作。

离散空间 gym.spaces.Discrete 类表示,

连续空间用 gym.spaces.Box 类表示。

基本执行流程如下

observation 是状态信息,是在游戏中观测到的屏幕像素值或者盘面状态描述信息。

reward 是奖励值,即动作提交以后能够获得的奖励值。这个奖励值因游戏的不同而不同,但总体原则是,对完成游戏有帮助的动作会获得比较高的奖励值。

done 表示游戏是否已经完成,如果完成了,就需要重置游戏并开始一个新的回合。

info 是一些比较原始的用于诊断和调试的信息,或许对训练有帮助。