深度 Q 网络(Deep - Q - Network) 介绍
在 Q-learning 算法中,当状态和动作空间是离散且维数不高时,可使用 Q-table 储存每个状态动作对的 Q 值,然后通过贝尔曼方差迭代求得每个状态动作对收敛的 Q 值,然后选择最优的动作当做策略。但是而当状态和动作空间是高维连续时,比如(游戏的状态动作对数目就很大)使用 Q-table 存储每个状态动作对就显得很不现实。
所以可以将 Q-Table 的更新问题变成一个函数拟合问题,相近的状态得到相近的输出动作。DQN 就是要设计一个神经网络结构,通过函数来拟合 Q 值。
下面引用一下自己写的一篇综述里面的 DQN 训练流程图,贴自己的图,不算侵犯版权吧,哈哈。知网上可以下载到这篇文章:http://kns.cnki.net/kcms/detail/detail.aspx?dbcode=CJFD&&filename=JSJX201801001。当时3个月大概看了百余篇DRL方向的论文,才写出来的,哈哈。
DQN 的亮点:
通过 experience replay(经验池)的方法来解决相关性及非静态分布问题,在训练深度网络时,通常要求样本之间是相互独立的,所以通过这种随机采样的方式,大大降低了样本之间的关联性,从而提升了算法的稳定性。
使用一个神经网络产生当前 Q 值,使用另外一个神经网络产生 Target Q 值。
DQN 损失函数和参数更新:
损失函数:
其中 yi 表示值函数的优化目标即目标网络的 Q 值:
参数更新的梯度为:
Tensorflow 2.0 实现 DQN
整体的代码是借鉴的莫烦大神,只不过现在用的接口都是 Tensorflow 2.0,所以代码显得很简单,风格很像 keras。
# -*- coding:utf-8 -*-
# Author : zhaijianwei
# Date : 2019/6/19 19:48
import tensorflow as tf
import numpy as np
from tensorflow.python.keras import layers
from tensorflow.python.keras.optimizers import RMSprop
from DQN.maze_env import Maze
class Eval_Model(tf.keras.Model):
def __init__(self, num_actions):
super().__init__('mlp_q_network')
self.layer1 = layers.Dense(10, activation='relu')
self.logits = layers.Dense(num_actions, activation=None)
def call(self, inputs):
x = tf.convert_to_tensor(inputs)
layer1 = self.layer1(x)
logits = self.logits(layer1)
return logits
class Target_Model(tf.keras.Model):
def __init__(self, num_actions):
super().__init__('mlp_q_network_1')
self.layer1 = layers.Dense(10, trainable=False, activation='relu')
self.logits = layers.Dense(num_actions, trainable=False, activation=None)
def call(self, inputs):
x = tf.convert_to_tensor(inputs)
layer1 = self.layer1(x)
logits = self.logits(layer1)
return logits
class DeepQNetwork:
def __init__(self, n_actions, n_features, eval_model, target_model):
self.params = {
'n_actions': n_actions,
'n_features': n_features,
'learning_rate': 0.01,
'reward_decay': 0.9,
'e_greedy': 0.9,
'replace_target_iter': 300,
'memory_size': 500,
'batch_size': 32,
'e_greedy_increment': None
}
# total learning step
self.learn_step_counter = 0
# initialize zero memory [s, a, r, s_]
self.epsilon = 0 if self.params['e_greedy_increment'] is not None else self.params['e_greedy']
self.memory = np.zeros((self.params['memory_size'], self.params['n_features'] * 2 + 2))
self.eval_model = eval_model
self.target_model = target_model
self.eval_model.compile(
optimizer=RMSprop(lr=self.params['learning_rate']),
loss='mse'
)
self.cost_his = []
def store_transition(self, s, a, r, s_):
if not hasattr(self, 'memory_counter'):
self.memory_counter = 0
transition = np.hstack((s, [a, r], s_))
# replace the old memory with new memory
index = self.memory_counter % self.params['memory_size']
self.memory[index, :] = transition
self.memory_counter += 1
def choose_action(self, observation):
# to have batch dimension when feed into tf placeholder
observation = observation[np.newaxis, :]
if np.random.uniform() < self.epsilon:
# forward feed the observation and get q value for every actions
actions_value = self.eval_model.predict(observation)
print(actions_value)
action = np.argmax(actions_value)
else:
action = np.random.randint(0, self.params['n_actions'])
return action
def learn(self):
# sample batch memory from all memory
if self.memory_counter > self.params['memory_size']:
sample_index = np.random.choice(self.params['memory_size'], size=self.params['batch_size'])
else:
sample_index = np.random.choice(self.memory_counter, size=self.params['batch_size'])
batch_memory = self.memory[sample_index, :]
q_next = self.target_model.predict(batch_memory[:, -self.params['n_features']:])
q_eval = self.eval_model.predict(batch_memory[:, :self.params['n_features']])
# change q_target w.r.t q_eval's action
q_target = q_eval.copy()
batch_index = np.arange(self.params['batch_size'], dtype=np.int32)
eval_act_index = batch_memory[:, self.params['n_features']].astype(int)
reward = batch_memory[:, self.params['n_features'] + 1]
q_target[batch_index, eval_act_index] = reward + self.params['reward_decay'] * np.max(q_next, axis=1)
# check to replace target parameters
if self.learn_step_counter % self.params['replace_target_iter'] == 0:
for eval_layer, target_layer in zip(self.eval_model.layers, self.target_model.layers):
target_layer.set_weights(eval_layer.get_weights())
print('\ntarget_params_replaced\n')
"""
For example in this batch I have 2 samples and 3 actions:
q_eval =
[[1, 2, 3],
[4, 5, 6]]
q_target = q_eval =
[[1, 2, 3],
[4, 5, 6]]
Then change q_target with the real q_target value w.r.t the q_eval's action.
For example in:
sample 0, I took action 0, and the max q_target value is -1;
sample 1, I took action 2, and the max q_target value is -2:
q_target =
[[-1, 2, 3],
[4, 5, -2]]
So the (q_target - q_eval) becomes:
[[(-1)-(1), 0, 0],
[0, 0, (-2)-(6)]]
We then backpropagate this error w.r.t the corresponding action to network,
leave other action as error=0 cause we didn't choose it.
"""
# train eval network
self.cost = self.eval_model.train_on_batch(batch_memory[:, :self.params['n_features']], q_target)
self.cost_his.append(self.cost)
# increasing epsilon
self.epsilon = self.epsilon + self.params['e_greedy_increment'] if self.epsilon < self.params['e_greedy'] \
else self.params['e_greedy']
self.learn_step_counter += 1
def plot_cost(self):
import matplotlib.pyplot as plt
plt.plot(np.arange(len(self.cost_his)), self.cost_his)
plt.ylabel('Cost')
plt.xlabel('training steps')
plt.show()
def run_maze():
step = 0
for episode in range(300):
# initial observation
observation = env.reset()
while True:
# fresh env
env.render()
# RL choose action based on observation
action = RL.choose_action(observation)
# RL take action and get next observation and reward
observation_, reward, done = env.step(action)
RL.store_transition(observation, action, reward, observation_)
if (step > 200) and (step % 5 == 0):
RL.learn()
# swap observation
observation = observation_
# break while loop when end of this episode
if done:
break
step += 1
# end of game
print('game over')
env.destroy()
if __name__ == "__main__":
# maze game
env = Maze()
eval_model = Eval_Model(num_actions=env.n_actions)
target_model = Target_Model(num_actions=env.n_actions)
RL = DeepQNetwork(env.n_actions, env.n_features, eval_model, target_model)
env.after(100, run_maze)
env.mainloop()
RL.plot_cost()
参考文献:
https://www.jianshu.com/p/10930c371cac
https://github.com/MorvanZhou/Reinforcement-learning-with-tensorflow
http://inoryy.com/post/tensorf
本文转载自 Alex-zhai 知乎账号。
原文链接:https://zhuanlan.zhihu.com/p/70009692
更多内容推荐
第四范式自动化推荐系统:搜索协同过滤中的交互函数
本文介绍第四范式研究组将自动化机器学习技术引入推荐系统中的一次尝试。
李宏毅深度强化学习课程:Deep Q-learning Advanced Tips
红色线表示DQN估计的Q值,发现都会比真实的Q值要高很多
基于神经网络 StarNet 的行人轨迹交互预测算法
本文介绍美团在基于神经网络StarNet的行人轨迹交互预测算法的研究。
07|模型工程:算法三大门派,取众家之长为我所用
目前,以深度学习模型为代表的连接主义派表现出色。然而,在许多情况下,AI系统仍然需要结合其他两个派别的算法,才能发挥最大的功效。
2023-08-25
11|VAE 系列:如何压缩图像给 GPU 腾腾地方
这一讲,我们将一起了解VAE的基本原理,之后我们训练自己的Stable Diffusion模型时,也会用上VAE这个模块。
2023-08-09
强化学习在推荐算法的应用论文整理(二)
传统的REINFORCE算法策略梯度
强化学习在推荐算法的应用论文整理(一)
本文将推荐的过程定义为一个序列决策的问题,通过Actor-Critic算法来进行 List-wise 的推荐。
颠覆者扩散模型:直观去理解加噪与去噪
扩散模型的工作原理是怎样的呢?算法优化目标是什么?与GAN相比有哪些异同?这一讲我们便从这些基础问题出发,开始我们的扩散模型学习之旅。
2023-07-28
李宏毅深度强化学习课程:Q-learning for Continuous Actions
传统的Q-learning的动作空间是离散的
强化学习入门——说到底研究的是如何学习
自机器学习重新火起来,深度强化学习就一直是科研的一大热点,也是最有可能实现通用人工智能的一个分支。
08|巧用神经网络:如何用 UNet 预测噪声
今天我就来为你解读UNet的核心知识。搞懂了这些,在你的日常工作中,便可以根据实际需求对预测噪声的模型做各种魔改了,也会为我们之后训练扩散模型的实战课打好基础。
2023-08-02
Q-learning 算法实践
使用强化学习算法,实现一个自动走迷宫机器人。
实现大规模图计算的算法思路
图神经网络这几年特别火爆,无论学术界还是业界,大家都在考虑用图神经网络。
24|GBDT+LR:排序算法经典中的经典
在前面的课程中,我们讲了推荐系统中的数据处理、接口实现和一些召回算法和模型,从本章开始,我们就会进入一个新的篇章:推荐系统中的排序算法。
2023-06-09
强化学习在美团“猜你喜欢”的实践
本文来自美团点评技术文章系列。
11|地球往事:为什么 CV 领域首先引领预训练潮流?
在这节课中,我们来学习视觉预训练模型PTM。
2023-09-04
深度度量学习中的损失函数
本文主要介绍一些常用的深度度量学习中使用的损失函数,同时了解它们是如何来给做困难样本挖掘的。
谷歌 AI 提出双重策略强化学习框架,帮助机器人安全学习动作技能
我们的目标是让机器人在现实世界中自主学习动作技巧,并且在学习过程中不会跌倒。
Deep Q
在当前状态s下使用策略 [公式] ,期望获得的累计奖赏。
京东:利用 DRL 算法进行带负反馈的商品推荐
大都数传统的推荐系统(协同过滤、基于内容的推荐、learning-to-rank)只是将推荐过程当做一个静态的过程
推荐阅读
27|DALL-E 3 技术探秘(二):从 unCLIP 到缝合怪方案
2023-11-09
强化学习从基础到进阶 - 常见问题和面试必知必答 [1]:强化学习概述、序列决策、动作空间定义、策略价值函数、探索与利用、Gym 强化学习实验
2023-06-19
5. 动态规划总论:状态设计的要点和技巧
2023-09-27
强化学习从基础到进阶 - 案例与实践 [4]:深度 Q 网络 -DQN、double DQN、经验回放、rainbow、分布式 DQN
2023-06-24
26|模型工程(二):算力受限,如何为“无米之炊”?
2023-10-18
强化学习从基础到进阶 - 案例与实践 [6]:演员 - 评论员算法(advantage actor-critic,A2C),异步 A2C、与生成对抗网络的联系等详解
强化学习基础篇 [3]:DQN、Actor-Critic 详细讲解
2023-06-03
电子书
大厂实战PPT下载
换一换 Meng-Ping Kao 高孟平 | 字节跳动 视频架构技术专家
王植萌 | 去哪儿网 基础架构技术高级总监
徐顺发 | 哈啰 前端技术专家
评论