什么是强化学习?
智能体(Agent,决策策略/算法/Q表可以理解为智能体的大脑)跟环境交互,在环境中做动作,由状态
S
i
S_i
Si变状态
S
i
+
1
S_{i+1}
Si+1,环境给予回报,智能体根据回报更新自己的”大脑“,不断在环境中探索,不断根据回报自我优化,慢慢的适应环境,达到预期最优。
什么是Q-learning?
一种经典的强化学习方法,定义了一个与状态,动作相关的值Q值,也叫 状态-动作值 ,它的意义是 在状态 s i s_i si下选择动作 a i a_i ai的价值。
实现方式是维护一个真实的Q表,是一个二维表格,记录每个动作下左右状态的Q值,决策时从当前状态下选择最大Q值对应的动作。 Q ( s , a ) ← Q ( s , a ) + α ( r + γ max π Q ( s ′ , a ′ ) − Q ( s , a ) ) Q(s,a)\gets Q(s,a)+\alpha(r+\gamma\underset{\pi}{\max}Q(s',a')-Q(s,a)) Q(s,a)←Q(s,a)+α(r+γπmaxQ(s′,a′)−Q(s,a)) 每次learn按照这个公式去一步步的更新Q表
Ql-eaning 案例 (莫烦Python)
import numpy as np
import pandas as pd
import time
np.random.seed(2) # 生成随机数
N_STATES = 6 # 状态数,次demo为一维空间,即6个状态
ACTIONS = ['left', 'right'] # 可进行的操作(左移动,右移动)
EPSILON = 0.9 # 贪婪率,当随机数大于这个数的时候会随机选择动作,小于这个数的时候会根据已经学习到的策略选择最优动作,即Q表的最大值
ALPHA = 0.1 # 学习效率
GAMMA = 0.9 # 奖励衰减(表示对未来奖励的重视程度)
MAX_EPISODES = 13 # 最大训练回合次数
FRESH_TIME = 0.3 # 速度
#创建q表
def build_q_table(n_states, actions):
table = pd.DataFrame(
np.zeros((n_states, len(actions))), # 初始化q_table
columns=actions, # 列索引名称actions【left,right】 行所以为默认值
)
return table
#选择动作
def choose_action(state, q_table):
state_actions = q_table.iloc[state, :]
#随机选择分支
if (np.random.uniform() > EPSILON) or ((state_actions == 0).all()):
action_name = np.random.choice(ACTIONS)
#最优选择分支
else:
action_name = state_actions.idxmax()
return action_name
def get_env_feedback(S, A):
# 环境交互
if A == 'right': #向右移动
if S == N_STATES - 2: # 代表到达终点
S_ = 'terminal'#S_为下一个状态
R = 1#奖励值
else:
S_ = S + 1
R = 0
else: # 向左移动
R = 0
if S == 0:
S_ = S
else:
S_ = S - 1
return S_, R
def update_env(S, episode, step_counter):
# 创建环境
env_list = ['-']*(N_STATES-1) + ['T'] # '---------T'
if S == 'terminal':
interaction = 'Episode %s: total_steps = %s' % (episode+1, step_counter)
print('\r{}'.format(interaction), end='')
time.sleep(2)
print('\r ', end='')
else:
env_list[S] = 'o'
interaction = ''.join(env_list)
print('\r{}'.format(interaction), end='')
time.sleep(FRESH_TIME)
def rl():
# 创建主循环
q_table = build_q_table(N_STATES, ACTIONS)
for episode in range(MAX_EPISODES):
step_counter = 0 #总步长
#起始位置
S = 0
is_terminated = False #设置标志位
update_env(S, episode, step_counter) #先更新环境
while not is_terminated:
A = choose_action(S, q_table) #选择动作
S_, R = get_env_feedback(S, A) # 进行移动并得到相应的奖励
q_predict = q_table.loc[S, A] #Q估计值
if S_ != 'terminal': #下一个状态不是终点
q_target = R + GAMMA * q_table.iloc[S_, :].max()#Q现实值
else:
q_target = R
is_terminated = True # 跳出while循环
q_table.loc[S, A] += ALPHA * (q_target - q_predict) # 更新环境反馈
S = S_ # 移动到下一位置
update_env(S, episode, step_counter+1)
step_counter += 1
return q_table
if __name__ == "__main__":
q_table = rl()
print('\r\nQ-table:\n')
print(q_table)