动态规划寻找最优策略

本文详细介绍了强化学习中的策略迭代、截断策略迭代和值迭代方法。这些方法基于马尔可夫决策过程和贝尔曼方程,旨在找到最优策略,使状态值最大。通过策略评估和策略改进,逐步优化智能体的行为。在不确定环境中,策略迭代不断评估和改进策略,直至收敛;截断策略迭代则在固定次数的迭代后停止评估;值迭代则同时进行策略评估和改进,直接更新状态值。每种方法都提供了具体的Python实现代码示例。
摘要由CSDN通过智能技术生成

本方法的基础是马尔可夫决策(MDP)和贝尔曼方程。本文目的在于找到一个使状态值最大的最优策略。本方法都是假设在不确定环境下做的测试,因此求的状态值是概率期望值。
本文描述的方法包括三种:普通的策略迭代、截断策略评估迭代和值迭代方法。
一、普通策略迭代方法
(1)迭代策略评估
用于对特定的策略求解其值函数。
其实现算法如下:
在这里插入图片描
有四个输入参数:
env:这是 OpenAI Gym 环境的实例,其中 env.P 会返回一步动态特性。
policy:这是一个二维 numpy 数组,其中 policy.shape[0] 等于状态数量 (env.nS) , policy.shape[1] 等于动作数量 (env.nA) 。policy[s][a] 返回智能体在状态 s 时根据该策略选择动作 a 的概率。
gamma:这是折扣率。它必须是在 0 到 1(含)之间的值,默认值为:1。
theta:这是一个非常小的正数,用于判断估算值是否足够地收敛于真值函数 (默认值为:1e-8)。
返回以下输出结果:
V:这是一个一维numpy数组,其中 V.shape[0] 等于状态数量 (env.nS)。V[s] 包含状态 s 在输入策略下的估计状态值。
实现代码如下

import numpy as np
def policy_evaluation(env, policy, gamma=1, theta=1e-8):
    V = np.zeros(env.nS)#初始值函数值状态假设为0
    while True:
        delta =0  #保证每次更新完所有状态点后归0,使每次得到所有状态点与前一次状态的差值,
        for s in range(env.nS):#更新到每个状态点
            vs = 0  #保证每次状态更新前归0
            for action,action_prob in enumerate(policy[s]):   #得到每个动作的概率   
                for prob,next_state,reward,done in env.P[s][action]: #得到一个状态下采取某个动作的下个状态和奖励和概率
                    vs += action_prob*prob*(reward+gamma*V[next_state]) #使用贝尔曼方程得到某个位置的状态
            delta = max(delta,np.abs(vs-V[s]))#找出所有差值的最大值
            V[s] = vs   
        if delta < theta:
            break      
    ## TODO: complete the function
    return V

(2)计算动作值函数
假设智能体在某一个状态已经确定了动作。但是确定了动作,下个状态和奖励还是不确定的。
实现算法如下:
在这里插入图片描述
有四个输入参数:
env:这是 OpenAI Gym 环境的实例,其中 env.P 会返回一步动态特性。
V:这是一个一维 numpy 数组,其中 V.shape[0] 等于状态数量 (env.nS)。V[s] 包含状态 s 的估值。
s:这是环境中的状态对应的整数。它应该是在 0 到 (env.nS)-1(含)之间的值。
gamma:这是折扣率。它必须是在 0 到 1(含)之间的值,默认值为:1。
返回以下输出结果:
q:这是一个一维 numpy 数组,其中 q.shape[0] 等于动作数量 (env.nA)。q[a] 包含状态 s 和动作 a 的(估算)值
实现代码如下:

def q_from_v(env, V, s, gamma=1):
    q = np.zeros(env.nA)
    
    ## TODO: complete the function
    for a in range(env.nA):
        vs = 0
        for prob,next_state,reward,done in env.P[s][a]:
            vs += prob*(reward+gamma*V[next_state]) 
        q[a]=vs
    
    return q

(3)策略改进
根据现有的策略得到的动作值估算状态值(state-value),并根据动作值最大的方向(0,1,2,3)返回改进的策略。
实现算法如下:
在这里插入图片描述
算法应该有三个输入参数:
env:这是 OpenAI Gym 环境的实例,其中 env.P 会返回一步动态特性。
V:这是一个一维 numpy 数组,其中 V.shape[0] 等于状态数量 (env.nS)。V[s] 包含状态 s 的估值。
gamma:这是折扣率。它必须是在 0 到 1(含)之间的值,默认值为:1。
该算法会返回以下输出结果:
policy:这是一个二维 numpy 数组,其中 policy.shape[0] 等于状态数量 (env.nS) , policy.shape[1] 等于动作数量 (env.nA) 。policy[s][a] 返回智能体在状态 s 时根据该策略选择动作 a 的概率。
实现代码如下:

def policy_improvement(env, V, gamma=1):
    policy = np.zeros([env.nS, env.nA]) / env.nA
    for s in range(env.nS):
        policy[s]=q_from_v(env,V,s,gamma)
       # index = policy[s].tolist().index(max(policy[s]))#只返回列表里的第一个值的index
        index = np.argwhere(policy[s]==max(policy[s]))
        policy[s] = np.zeros_like(policy[s])
        policy[s][index]=1
        policy[s]=policy[s]/sum(policy[s])
    #print(policy)  
    ## TODO: complete the function
    return policy
print(policy_improvement(env, V, gamma=1))

(4)策略迭代
策略跌代就是重复进行策略评估(根据策略计算状态值),然后根据得到的状态值计算动作值,并进行策略改进。直到策略不再发生改变。
实现算法如下:
在这里插入图片描述
实现代码如下:
有三个输入参数:
env:这是 OpenAI Gym 环境的实例,其中 env.P 会返回一步动态特性。
gamma:这是折扣率。它必须是在 0 到 1(含)之间的值,默认值为:1。
theta:这是一个非常小的正数,用于判断策略评估步骤是否足够地收敛于真值函数 (默认值为:1e-8)。
返回以下输出结果:
policy:这是一个二维 numpy 数组,其中 policy.shape[0] 等于状态数量 (env.nS) , policy.shape[1] 等于动作数量 (env.nA) 。policy[s][a] 返回智能体在状态 s 时根据该策略选择动作 a 的概率。
V:这是一个一维 numpy 数组,其中 V.shape[0] 等于状态数量 (env.nS)。V[s] 包含状态 s 的估值。

import copy
def policy_iteration(env, gamma=1, theta=1e-8):
    policy = np.ones([env.nS, env.nA]) / env.nA
    ## TODO: complete the function
    i = 0
    while True:
        i = i + 1
        V = policy_evaluation(env,policy,gamma,theta)
        policy_new = policy_improvement(env,V,gamma)
        if (policy_new == policy).all():
            print(i)
            break
        policy = policy_new 
    return policy, V

二、截断策略评估迭代
在对状态空间执行固定次数的遍历后,停止评估步骤,从而将此方法称为截断策略评估。
(1) 截断策略状态值评估
截断策略评估算法如下:
在这里插入图片描述
实现代码如下:
env:这是 OpenAI Gym 环境的实例,其中 env.P 会返回一步动态特性。
policy:这是一个二维 numpy 数组,其中 policy.shape[0] 等于状态数量 (env.nS) , policy.shape[1] 等于动作数量 (env.nA) 。policy[s][a] 返回智能体在状态 s 时根据该策略选择动作 a 的概率。
V:这是一个一维 numpy 数组,其中 V.shape[0] 等于状态数量 (env.nS)。V[s] 包含状态 s 的估值。
max_it:这是一个正整数,对应的是经历状态空间的次数(默认值为:1)。
gamma:这是折扣率。它必须是在 0 到 1(含)之间的值,默认值为:1。
返回以下输出结果:
V:这是一个一维 numpy 数组,其中 V.shape[0] 等于状态数量 (env.nS)。V[s] 包含状态 s 的估值。

def truncated_policy_evaluation(env, policy, V, max_it=1, gamma=1):
    ## TODO: complete the function
    i = 0
    while i < max_it:
        for s in range(env.nS):
            vs = 0
            for a,action_prob in enumerate(policy[s]):
                for prob,next_state,reward,done in env.P[s][a]:
                    vs += action_prob*prob*(reward+gamma*V[next_state])
            V[s] = vs
            i = i+1
    return V

(2)截断策略迭代
实现算法如下:
在这里插入图片描述
实现代码如下:
env:这是 OpenAI Gym 环境的实例,其中 env.P 会返回一步动态特性。
max_it:这是一个正整数,对应的是经历状态空间的次数(默认值为:1)。
gamma:这是折扣率。它必须是在 0 到 1(含)之间的值,默认值为:1。
theta:这是一个非常小的正整数,用作停止条件(默认值为:1e-8)。
返回以下输出结果:
policy:这是一个二维 numpy 数组,其中 policy.shape[0] 等于状态数量 (env.nS) , policy.shape[1] 等于动作数量 (env.nA) 。policy[s][a] 返回智能体在状态 s 时根据该策略选择动作 a 的概率。
V:这是一个一维 numpy 数组,其中 V.shape[0] 等于状态数量 (env.nS)。V[s] 包含状态 s 的估值。

  def truncated_policy_iteration(env, max_it=10, gamma=1, theta=1e-8):
    V = np.zeros(env.nS)
    policy = np.zeros([env.nS, env.nA]) / env.nA
    while True:
        policy = policy_improvement(env,V,gamma)
        V_old = copy.deepcopy(V)  #必须使用copy()或者deepcopy(),使用'='只是引用,改变V本身也会改变v_old
        V = truncated_policy_evaluation(env,policy,V,max_it,gamma)#改变v是通过改变V的每一项改变V的,如果是用'='会导致v_old与v同步变化.
        delta = max(abs(V_old-V))                    #为了保证v_old与v不同步变化,我们使用浅copy()or deepcopy()
        if delta<theta:
            break
    ## TODO: complete the function    
    return policy, V

三、值迭代
在动态规划设置中用来估算不同策略对应的状态值。每次对状态空间进行遍历时,都会同时进行策略评估和策略改进。在该算法中,会把求得的每个状态的最大动作值直接作为新的状态值,从而免去了策略改进的步骤,同时会在最后根据最终状态值得到最优策略。
实现算法如下:
在这里插入图片描述
实现代码如下:
env:这是 OpenAI Gym 环境的实例,其中 env.P 会返回一步动态特性。
gamma:这是折扣率。它必须是在 0 到 1(含)之间的值,默认值为:1。
theta:这是一个非常小的正整数,用作停止条件(默认值为:1e-8)。
返回以下输出结果:
policy:这是一个二维 numpy 数组,其中 policy.shape[0] 等于状态数量 (env.nS) , policy.shape[1] 等于动作数量 (env.nA) 。policy[s][a] 返回智能体在状态 s 时根据该策略选择动作 a 的概率。
V:这是一个一维 numpy 数组,其中 V.shape[0] 等于状态数量 (env.nS)。V[s] 包含状态 s 的估值。

def value_iteration(env, gamma=1, theta=1e-8):
    V = np.zeros(env.nS)
    
    ## TODO: complete the function
    while True:
        delta = 0
        for s in range(env.nS):
            V_old = copy.copy(V[s])
            q = q_from_v(env,V,s,gamma)
            V[s] = max(q)
            delta = max(delta,abs(V[s]-V_old))
        if delta < theta:
            policy = policy_improvement(env,V,gamma)
            break
    return policy, V
    ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

智能学习者

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值