强化学习课程学习(8)——基于连续动作空间上的方法求解RL

策略梯度提供了和DQN之类的方法不同的新思路,但是我们上面的蒙特卡罗策略梯度reinforce算法却并不完美。由于是蒙特卡罗法,我们需要完全的序列样本才能做算法迭代,同时蒙特卡罗法使用收获的期望来计算状态价值,会导致行为有较多的变异性,我们的参数更新的方向很可能不是策略梯度的最优方向。这时可以考虑结合value-based强化学习方法来解决——AC算法

强化学习课程学习(8)——基于连续动作空间上的方法求解RL_第1张图片

Actor-Critic

Policy Based+Value Based结合的策略梯度方法Actor-Critic从名字上看包括两部分,演员(Actor)评价者(Critic)。其中Actor使用我们上一节讲到的策略函数,负责生成动作(Action)``并和环境交互。而Critic使用我们之前讲到了的价值函数,负责评估Actor的表现,并指导Actor下一阶段的动作。具体算法思路和详细理解暂时不阐述,后续需要用到实际场景中再根据针对性地去详细深入挖掘——

基本版的Actor-Critic算法虽然思路很好,但是由于难收敛的原因,还需要做改进。

目前改进的比较好的有两个经典算法,一个是DDPG`算法,使用了`双Actor神经网络双Critic神经网络的方法来改善收敛性。这个方法我们在从DQN`到`Nature DQN`的过程中已经用过一次了。另一个是`A3C算法,使用了多线程的方式,一个主线程负责更新Actor和Critic的参数,多个辅线程负责分别和环境交互,得到梯度更新值,汇总更新主线程的参数。而所有的辅线程会定期从主线程更新网络参数。这些辅线程起到了类似``DQN`中经验回放的作用,但是效果更好。

A3C

回放池经验数据相关性太强,用于训练的时候效果很可能不佳。举个例子,我们学习下棋,总是和同一个人下,期望能提高棋艺。这当然没有问题,但是到一定程度就再难提高了,此时最好的方法是另寻高手切磋。这时Asynchronous Advantage Actor-critic(以下简称A3C)算法可以解决这个问题,A3C避免了经验回放相关性过强的问题,同时做到了异步并发的学习模型。

相比Actor-Critic,A3C的优化主要有3点:

  • 异步训练框架

  • 网络结构优化

  • Critic评估点的优化

    其中异步训练框架是最大的优化。

DDPG

A3C算法使用多线程的方法来解决Actor-Critic难收敛的问题,DDPG算法不使用多线程,而是使用和DDQN类似的方法:即经验回放双网络的方法来改进Actor-Critic难收敛的问题。

深度确定性策略梯度(Deep Deterministic Policy Gradient,DDPG),从DDPG这个名字看,它是由D(Deep)+D(Deterministic )+ PG(Policy Gradient)组成。确定性策略是和随机策略相对而言的,对于某一些动作集合来说,它可能是连续值,或者非常高维的离散值,这样动作的空间维度极大。如果我们使用随机策略,即像``DQN`一样研究它所有的可能动作的概率,并计算各个可能的动作的价值的话,那需要的样本量是非常大才可行的。于是有人就想出使用确定性策略来简化这个问题。作为随机策略,在相同的策略,在同一个状态处,采用的动作是基于一个概率分布的,即是不确定的。而确定性策略则决定简单点,虽然在同一个状态处,采用的动作概率不同,但是最大概率只有一个,如果我们只取最大概率的动作,去掉这个概率分布,那么就简单多了。即作为确定性策略,相同的策略,在同一个状态处,动作是唯一确定的,即策略变成:
π θ ( s ) = a \pi_{\theta}(s) = a πθ(s)=a
总结如下:

  • DDPG的提出动机其实是为了让DQN可以扩展到连续的动作空间。
  • DDPG借鉴了DQN的两个技巧:经验回放 和 固定Q网络。
  • DDPG使用策略网络直接输出确定性动作。
  • DDPG使用了Actor-Critic的架构。

DDPG算法实例

使用DDPG解决连续控制版本的CartPole问题,给小车一个力(连续量)使得车上的摆杆倒立起来。
核心代码如下:

  • 设置超参数
# pip install gym
# pip install paddlepaddle==1.6.3
# pip install parl==1.3.1
ACTOR_LR = 1e-3  # Actor网络的 learning rate
CRITIC_LR = 1e-3  # Critic网络的 learning rate

GAMMA = 0.99      # reward 的衰减因子
TAU = 0.001       # 软更新的系数
MEMORY_SIZE = int(1e6)                  # 经验池大小
MEMORY_WARMUP_SIZE = MEMORY_SIZE // 20  # 预存一部分经验之后再开始训练
BATCH_SIZE = 128
REWARD_SCALE = 0.1   # reward 缩放系数
NOISE = 0.05         # 动作噪声方差

TRAIN_EPISODE = 6000 # 训练的总episode数
  • 搭建ModelAlgorithmAgent架构
    • Agent把产生的数据传给algorithmalgorithm根据model的模型结构计算出Loss,使用SGD或者其他优化器不断的优化,PARL这种架构可以很方便的应用在各类深度强化学习问题中。
    • Model用来定义前向(Forward)网络,用户可以自由的定制自己的网络结构
    • Algorithm定义了具体的算法来更新前向网络(Model),也就是通过定义损失函数来更新Model,和算法相关的计算都放在algorithm`中。
class Model(parl.Model):
    def __init__(self, act_dim):
        self.actor_model = ActorModel(act_dim)
        self.critic_model = CriticModel()

    def policy(self, obs):
        return self.actor_model.policy(obs)

    def value(self, obs, act):
        return self.critic_model.value(obs, act)

    def get_actor_params(self):
        return self.actor_model.parameters()


class ActorModel(parl.Model):
    def __init__(self, act_dim):
        hid_size = 100

        self.fc1 = layers.fc(size=hid_size, act='relu')
        self.fc2 = layers.fc(size=act_dim, act='tanh')

    def policy(self, obs):
        hid = self.fc1(obs)
        means = self.fc2(hid)
        return means


class CriticModel(parl.Model):
    def __init__(self):
        hid_size = 100

        self.fc1 = layers.fc(size=hid_size, act='relu')
        self.fc2 = layers.fc(size=1, act=None)

    def value(self, obs, act):
        concat = layers.concat([obs, act], axis=1)
        hid = self.fc1(concat)
        Q = self.fc2(hid)
        Q = layers.squeeze(Q, axes=[1])
        return Q

以上所有版本的代码都是基于百度开发的paddlepaddleparl框架实现的,版本是paddlepaddle=1.6.3parl=1.3.1!

感谢百度AI studio提供学习资料和平台,感谢科科老师的讲解!

你可能感兴趣的:(强化学习,深度学习)