克隆成功是否进入此策略?

确定取消

量化投资:基于强化学习的GridWorld(代码+思路)

发布于2018-08-06 10:00 浏览 155 评论 0 1 0 分享到:

四个函数表达式(下文中的行动也可称为决策):

函数一、状态-价值函数:

函数二、行动-价值函数:(虽然这里没有对下式进行展开,但是如果展开的话,就是上式除掉第一个求和符号和及π(a|s))

函数三、最优状态-价值函数:

函数四、最优行动-价值函数:

现在来对以上四个函数表达式做一点补充说明:

其中的p(s’|s,a)是状态转移概率;

其中的r是由状态s到达状态s’获得的回报值;

其中的π(a|s)是指处在状态s时作出a行动的概率;

值得注意的是,我们使用以上明确的函数式来处理强化学习任务的时候,一般是只能处理有限状态的马尔科夫决策过程。接下来我们看一个简单的有限状态的马尔科夫决策过程实例。

这是一个GridWorld问题,如上图所示是一个包含5*5个元胞的网格,在每一个元胞内,agent都有四种行动可以执行,它们分别是“上”、“下”、“左”、“右”。假设agent在每个格子处采取四种行动的概率是相同的,同时未来回报的折扣因子设为0.9,而agent的状态转移以及回报值分为以下四种情况:

如果agent在边缘处,那么如果它此时执行的动作使它溢出网格的话,我们限制它的位置仍然固定不变,但是同时它会得到-1的回报值;

如果agent处在A点,那么它的任意行动都将得到10的回报值,同时下一步的状态移至A’处;

如果agent处在B点,那么它的任意行动都将得到5的回报值,同时下一步的状态移至B’处;

其他情况则会得到0的回报值,状态转移遵从格子的位置变化;

根据以上提示,我们如何计算每个元胞的状态-价值函数(函数一)以及最优状态-价值函数(函数三)呢?

一、计算状态-价值函数

在正式开始写代码之前,我们需要理解状态-价值函数的含义。所谓状态-价值函数,在这里我们不妨理解为agent处在每个格子的时候未来得到的回报值。直观上来分析,我们可以很容易得出以下三条判断:

显然agent处在A和B处的时候状态-价值应该要大一些,为什么呢?因为当agent处在A或B时,下一步无论它采取什么行动,都会得到较大的10或5回报值。

那么,对于其他元胞的状态-价值呢?我们可以这样思考,既然A和B处的状态-价值较大,那么A或B附近处的元胞的状态-价值也肯定比远离A或B处元胞的状态-价值要大。

还有一点就是,既然边缘处很容易得到-1的回报值,那么显然边缘处的元胞要比内部的元胞的状态-价值要小。

除此之外,我们还应该明白,在计算状态-价值函数的时候,我们是不用区分具体行动的,换句话说我们只用按照题意中的均匀概率进行决策即可。那么,每个元胞的状态-价值函数当然是包含了处在该元胞处的所有行动,因此,我们需要在遵从均匀随机决策下对所有行动进行迭代,直到所有元胞的状态-价值收敛为止,这种做法叫做迭代策略评估。

另外一点需要注意的是,在贝尔曼方程中,有一个量P(s’|s,a)是状态转移概率,而在这里这个量的值是1,原因是按照题意,每一个元胞的每一个行动都转移到唯一的下个状态,而不是随机的。

明白了以上的要点,代码写起来就很轻松了,求解状态-价值函数直接按照贝尔曼方程,进行如下迭代即可:

二、计算最优状态-价值函数

所谓最优状态-价值函数其实很好理解,一方面在数学公式上很好理解,直接对a进行迭代并取最大值即可,而且相比状态-价值函数省去了概率π(a|s)的计算;而直观上我们也可以这么想,前面我们计算的状态-价值函数实际上并没有给出当agent处于每个元胞时候下一步怎么走获得价值最大,而只是给出了当agent处于每个元胞的平均价值,即包含了下一步所有可能的行动。

计算最优状态-价值函数就是要找出agent在每个元胞处它下一步该采取什么行动可以保证状态-价值最大。按照贝尔曼最优方程,我们只用对行动a进行迭代即可,并且找出最大的价值,重复迭代,直到收敛为止。

三、实验结果

首先,计算出的状态-价值函数值如下。这个结果与我们最初的直观判断也很一致。

我将以上结果使用灰度图可视化一下,得到以下图,颜色越深处表明状态-价值越大。

同样的,计算出的最优状态-价值函数值如下:

将其可视化如下:

并且,得到的每个元胞的最优行动如下(U、D、L、R分别代表上、下、左、右):

四、代码实践

代码编写步骤如下:

1.定义好所有状态转移以及对应回报值(此处调用了printboard函数,详情请见源代码):

  1. #coding=utf-8
  2. import numpy as np
  3. import argparse
  4. from utils import printboard
  5. import matplotlib.pyplot as plt
  6. plt.rcParams['axes.facecolor'] = 'white'# 命令行接收参数parser = argparse.ArgumentParser()
  7. parser.add_argument('--grid_size', type=int, default=5,
  8. help='set size of grid stateValue')
  9. parser.add_argument('--discount', type=float, default=0.9,
  10. help='set discount factor of future expected reward')
  11. parser.add_argument('--posA', type=list, default=[0, 1],
  12. help='set position of A')
  13. parser.add_argument('--posB', type=list, default=[0, 3],
  14. help='set position of B')
  15. parser.add_argument('--primeA', type=list, default=[4, 1],
  16. help='set prime position of A')
  17. parser.add_argument('--primeB', type=list, default=[2, 3],
  18. help='set prime position of B')
  19. args = parser.parse_args()
  20. grid_size = args.grid_size
  21. posA = args.posA
  22. primeA = args.primeA
  23. posB = args.posB
  24. primeB = args.primeB
  25. discount = args.discount# 四种可能的决策# left, up, right, downactions = ['L', 'U', 'R', 'D']
  26. actionProb = []# 定义好每个状态处的行动概率,即均匀随机决策
  27. for i in range(0, grid_size):
  28. actionProb.append([])
  29. for j in range(0, grid_size):
  30. actionProb[i].append(dict({'L':0.25, 'U':0.25, 'R':0.25, 'D':0.25}))
  31. # 定义好每个状态处的状态转移,以及回报值
  32. successorState = []
  33. actionReward = []
  34. for i in range(0, grid_size):
  35. successorState.append([])
  36. actionReward.append([])
  37. for j in range(0, grid_size):
  38. next = dict()
  39. reward = dict()
  40. # 其他元胞上下左右以及注意边缘处行动要保持不变
  41. if i == 0:
  42. next['U'] = [i, j]
  43. reward['U'] = -1.0
  44. else:
  45. next['U'] = [i - 1, j]
  46. reward['U'] = 0.0
  47. if i == grid_size - 1:
  48. next['D'] = [i, j]
  49. reward['D'] = -1.0
  50. else:
  51. next['D'] = [i + 1, j]
  52. reward['D'] = 0.0
  53. if j == 0:
  54. next['L'] = [i, j]
  55. reward['L'] = -1.0
  56. else:
  57. next['L'] = [i, j - 1]
  58. reward['L'] = 0.0
  59. if j == grid_size - 1:
  60. next['R'] = [i, j]
  61. reward['R'] = -1.0
  62. else:
  63. next['R'] = [i, j + 1]
  64. reward['R'] = 0.0
  65. # 定义A、B处的状态转移以及回报值
  66. # 同时,将上面边缘处的限制覆盖
  67. if [i, j] == posA:
  68. next['L'] = next['R'] = next['D'] = next['U'] = primeA
  69. reward['L'] = reward['R'] = reward['D'] = reward['U'] = 10.0
  70. if [i, j] == posB:
  71. next['L'] = next['R'] = next['D'] = next['U'] = primeB
  72. reward['L'] = reward['R'] = reward['D'] = reward['U'] = 5.0
  73. successorState[i].append(next)
  74. actionReward[i].append(reward)
  1. 按照贝尔曼方程计算状态-价值函数并可视化:
  1. stateValue = np.zeros((grid_size, grid_size))
  2. while True:
  3. newStateValue = np.zeros((grid_size, grid_size))
  4. for i in range(0, grid_size):
  5. for j in range(0, grid_size):
  6. for action in actions:
  7. newPosition = successorState[i][j][action]
  8. newStateValue[i, j] += actionProb[i][j][action] * (actionReward[i][j][action] + discount * stateValue[newPosition[0], newPosition[1]])
  9. if np.sum(np.abs(stateValue - newStateValue)) < 1e-4:
  10. print('均匀随机策略:状态-价值')
  11. print(newStateValue)
  12. break
  13. stateValue = newStateValue
  14. plt.matshow(newStateValue, cmap=plt.cm.Greys)
  15. plt.colorbar()
  16. plt.title('state value')
  17. plt.show()
  1. 按照贝尔曼优化方程计算最优状态-价值函数并可视化:
  1. stateValue = np.zeros((grid_size, grid_size))
  2. while True:
  3. newStateValue = np.zeros((grid_size, grid_size))
  4. a = ''
  5. for i in range(0, grid_size):
  6. for j in range(0, grid_size):
  7. values = []
  8. for action in actions:
  9. newPosition = successorState[i][j][action]
  10. values.append(actionReward[i][j][action] + discount * stateValue[newPosition[0], newPosition[1]])
  11. newStateValue[i][j] = np.max(values)
  12. # 找出所有最优状态-价值的行动
  13. indexes = np.argwhere(values == np.max(values))
  14. indexes = indexes.flatten().tolist()
  15. policyOfState = ''.join([actions[index] for index in indexes])
  16. a += policyOfState+' '
  17. if np.sum(np.abs(stateValue - newStateValue)) < 1e-4:
  18. a = a.strip().split(' ')
  19. policy = np.reshape(a,[grid_size, grid_size])
  20. print('均匀随机策略:最优状态-价值')
  21. print(newStateValue)
  22. printboard(policy)
  23. break
  24. stateValue = newStateValue
  25. plt.matshow(newStateValue, cmap=plt.cm.Greys)
  26. plt.colorbar()
  27. plt.title('optimal state value')
  28. plt.show()

原文链接:http://t.cn/RD2cIvp

0 个评论

发表评论