目录
AlphaGo概述
首先认识围棋中的一些内容:
围棋的棋盘由
19
×
19
19\times 19
19×19的网格组成,因此,包含361个点,围棋竞技的状态就是黑白棋子在空间上的排列。直观的进行建模,我们可以用
19
×
19
×
2
19\times 19\times 2
19×19×2的张量表示当前状态,其中,
19
×
19
×
1
19\times 19\times 1
19×19×1张量代表黑棋子方,其中的值0和1代表有无放棋子;同理,另外
19
×
19
×
1
19\times 19\times 1
19×19×1张量代表白棋子方(也是0和1代表有无放棋子)。
在AlphaGo中,实际是用 19 × 19 × 17 19\times 19\times 17 19×19×17的张量保存状态,额外的通道用于反映其他信息。
对于动作,则是将棋子放到棋盘的空闲点上,动作的集合为棋盘上点的编号: A = { 1 , 2 , 3 , . . . , 361 } A=\left\{1,2,3,...,361\right\} A={1,2,3,...,361}在围棋中,可能的动作序列一共 1 0 170 10^{170} 10170种,这是暴力搜索不能解决的问题,因此采用深度强化学习实现AlphaGo。
下面大致介绍AlphaGo的设计思路。
首先是训练,包含3个步骤:
- 1.行为克隆(behavior cloning)初始化策略网络,行为克隆不是强化学习,而是一个动作分类任务(深度学习种的有监督学习),使用的标注数据为16万局真人对决记录。
- 2.使用Policy Gradient训练策略网络:实例化两个步骤1中的策略网络进行相互博弈。
- 3.不同于Actor-Critic Methods,AlphaGo没有同时训练策略网络和价值网络,AlphaGo先训练好策略网络,再利用策略网络训练价值网络。
在AlphaGo实际下棋时,通过策略网络和价值网络指导蒙特卡洛树搜索方法(Monte Carlo Tree Search,MCTS)进行动作搜索。
AlphaGo的Policy Network
网络结构
在AlphaGo中,使用
19
×
19
×
17
19\times 19\times 17
19×19×17的张量表示state:
该张量具有以下设计思想:
黑棋子有8个通道,第一个通道为当前回合的棋子位置状态,0表示对应位置没有棋子,1表示有棋子,剩下7个通道为前7个回合的棋子位置状态;
白棋子同理,也有8个通道;
最后一个通道反映当前轮到哪一方做动作,如果轮到黑棋方,就为全1的矩阵,反之,如果轮到白棋方,就为全0的矩阵;
根据以上分析,AlphaGo的策略网络如下:
策略网络输入state的张量(
19
×
19
×
17
19\times 19\times 17
19×19×17),输出361个动作组成的概率分布。
训练方法
Behavior Cloning预训练
AlphaGo训练策略网络的第一步是Behavior Cloning,一开始,网络的参数都是随机初始化。如果在这个时候让两个策略网络进行博弈,它们的动作都是完全随机的,因此需要非常非常长期的时间才能具备生成有意义的动作分布。
为了解决这个问题,AlphaGo采用有监督学习对策略网络进行预训练,通过收集16万局真人对决记录作为有标签的数据,训练策略网络。这个方法被称为Behavior Cloning,经过训练后的网络不能对抗职业玩家,但已经能够打败业余玩家。
注意Behavior Cloning不是强化学习,强化学习的监督信号来自环境给agent的奖励,Behavior Cloning属于模仿学习(Imitation Learning)。对于Behavior Cloning,agent不关心环境的奖励,只需要依照顺序模仿动作(按顺序进行动作分类)即可。
Behavior Cloning的具体过程如下:
- 观测到当前状态 s t s_{t} st;
- 使用策略网络输出动作的概率分布: p t = [ π ( 1 ∣ s t ; θ ) , . . . , π ( 361 ∣ s t ; θ ) ] ∈ ( 0 , 1 ) 361 p_{t}=[\pi(1|s_{t};\theta),...,\pi(361|s_{t};\theta)]\in (0,1)^{361} pt=[π(1∣st;θ),...,π(361∣st;θ)]∈(0,1)361
- 假设标注的动作为落在第281号点上,标注动作记录为 a t ∗ = 281 a^{*}_{t}=281 at∗=281,现在对 a t ∗ a^{*}_{t} at∗进行one-hot编码得到向量 y t ∈ { 0 , 1 } 361 y_{t}\in\left\{0,1\right\}^{361} yt∈{0,1}361;
- 计算交叉熵损失: L o s s = C r o s s E n t r o p y ( y t , p t ) Loss=CrossEntropy(y_{t},p_{t}) Loss=CrossEntropy(yt,pt)使用该损失计算梯度并更新参数 θ \theta θ。
现在思考问题:Behavior Cloning训练策略网络后,还需要用强化学习继续训练策略网络,那么Behavior Cloning到底差在哪里?
- 解释:强化学习是以环境给agent的奖励为监督信号的,但Behavior Cloning属于传统的有监督学习,它只能对以前见过的状态有良好表现(只有在训练集中见过的类似状态,网络才能输出合理的概率分布),围棋的状态是极为复杂的,16万局的游戏只算是围棋所有状态中的冰山一角,如果仅使用Behavior Cloning训练网络,在实际围棋对决时,如果遇到陌生状态,模型将很容易输出错误的动作概率分布。
使用Policy Gradient继续训练策略网络
研究人员用两个策略网络进行博弈:一个叫做Player(Agent),另一个叫做Opponent(Environment):
Player是具有最新参数的策略网络,Opponent也是策略网络,但每一局使用的参数都是随机从过去Player参数中选择的。
我们让Player和Opponent进行博弈,直到游戏结束,假设走了 T T T步之后游戏结束,游戏结束前,任意步的奖励均为0: r 1 = r 2 = ⋅ ⋅ ⋅ = r T − 1 = 0 r_{1}=r_{2}=\cdot\cdot\cdot=r_{T-1}=0 r1=r2=⋅⋅⋅=rT−1=0如果Agent赢了,则有 r T = + 1 r_{T}=+1 rT=+1,如果Agent输了,则有 r T = − 1 r_{T}=-1 rT=−1。
回顾回报的定义: u t = ∑ i = t T r i u_{t}=\sum_{i=t}^{T}r_{i} ut=i=t∑Tri这意味着,如果agent赢了,则有: u 1 = u 2 = ⋅ ⋅ ⋅ = u T = + 1 u_{1}=u_{2}=\cdot\cdot\cdot=u_{T}=+1 u1=u2=⋅⋅⋅=uT=+1如果agent输了,则有: u 1 = u 2 = ⋅ ⋅ ⋅ = u T = − 1 u_{1}=u_{2}=\cdot\cdot\cdot=u_{T}=-1 u1=u2=⋅⋅⋅=uT=−1这样的设计意义为:只要最后能赢,就认为这局比赛的agent每一步动作都是好棋。
回顾策略梯度算法,目标是计算状态-价值函数 V ( s ; θ ) V(s;\theta) V(s;θ)关于参数 θ \theta θ的梯度,但我们可以用下面式子近似策略梯度: ∂ l o g π ( a t ∣ s t ; θ ) ∂ θ ⋅ Q π ( s t , a t ) \frac{\partial log\pi(a_{t}|s_{t};\theta)}{\partial\theta}\cdot Q_{\pi}(s_{t},a_{t}) ∂θ∂logπ(at∣st;θ)⋅Qπ(st,at)其中, Q π ( s t , a t ) Q_{\pi}(s_{t},a_{t}) Qπ(st,at)是动作-价值函数,其本质是折扣回报的期望: Q π ( s t , a t ) = E [ U t ∣ s t , a t ] Q_{\pi}(s_{t},a_{t})=E[U_{t}|s_{t},a_{t}] Qπ(st,at)=E[Ut∣st,at]因此,对于一局游戏,我们可以用观测值 u t u_{t} ut(要么为+1,要么为-1)近似 Q π ( s t , a t ) Q_{\pi}(s_{t},a_{t}) Qπ(st,at),此时,可以进一步得到策略梯度的近似: ∂ l o g π ( a t ∣ s t ; θ ) ∂ θ ⋅ u t \frac{\partial log\pi(a_{t}|s_{t};\theta)}{\partial\theta}\cdot u_{t} ∂θ∂logπ(at∣st;θ)⋅ut总结一下训练策略网络的步骤:
- 用两个策略网络进行博弈直到游戏结束(Player v.s. Opponent);
- 记录agent(Player)的轨迹: s 1 , a 1 , s 2 , a 2 , . . . , s T , a T s_{1},a_{1},s_{2},a_{2},...,s_{T},a_{T} s1,a1,s2,a2,...,sT,aT
- 根据agent的输赢结果得到回报: u 1 = u 2 = ⋅ ⋅ ⋅ = u T u_{1}=u_{2}=\cdot\cdot\cdot=u_{T} u1=u2=⋅⋅⋅=uT如果赢了,则全为+1,输了则全为-1;
- 累加近似的策略梯度: g θ = ∑ t = 1 T ∂ l o g π ( a t ∣ s t ; θ ) ∂ θ ⋅ u t g_{\theta}=\sum_{t=1}^{T}\frac{\partial log\pi(a_{t}|s_{t};\theta)}{\partial\theta}\cdot u_{t} gθ=t=1∑T∂θ∂logπ(at∣st;θ)⋅ut
- 梯度上升更新Player的参数: θ = θ + β ⋅ g θ \theta=\theta+\beta\cdot g_{\theta} θ=θ+β⋅gθ
使用策略网络下棋
铺垫内容
经过强化学习训练后,得到策略网络 π \pi π,可以用来下棋,观测到当前的状态 s t s_{t} st,随机抽样动作: a t ∼ π ( ⋅ ∣ s t ; θ ) a_{t}\sim\pi(\cdot|s_{t};\theta) at∼π(⋅∣st;θ)此时的策略网络已经足够强大,但是还不能击败围棋冠军,这是因为面对围棋冠军时,策略网络的小概率不稳定性会导致走错某一步,走错一步可能就导致围棋局势发生改变。
比策略网络抽样更稳定的方法是蒙特卡洛树搜索,为了实现蒙特卡洛树搜索,还需要学习一个价值网络,这个价值网络不同于价值学习中的价值网络,这个价值网络是状态-价值网络(价值学习中的是最优动作-价值网络 Q ∗ Q^{*} Q∗)
训练State-Value Network
先回顾状态-价值函数,已知动作-价值函数: Q π ( s t , a t ) = E [ U t ∣ S t = s t , A t = a t ] Q_{\pi}(s_{t},a_{t})=E[U_{t}|S_{t}=s_{t},A_{t}=a_{t}] Qπ(st,at)=E[Ut∣St=st,At=at]而状态-价值函数为: V π ( s t ) = E A [ Q π ( s t , A ) ] V_{\pi}(s_{t})=E_{A}[Q_{\pi}(s_{t},A)] Vπ(st)=EA[Qπ(st,A)]其中,如果agent赢了则 u t = + 1 u_{t}=+1 ut=+1,否则 u t = − 1 u_{t}=-1 ut=−1;
现在用神经网络 v ( s ; w ) v(s;w) v(s;w)近似状态-价值函数 V π ( s ) V_{\pi}(s) Vπ(s),它用于衡量当前状态的好坏。
此时发现,AlphaGo其实是两个网络的组合,它们共享卷积层,全连接一个分支用于策略网络,一个用于价值网络:
策略网络输出动作的概率分布,价值网络输出当前状态好坏程度的得分。并且要注意,策略网络和价值网络不是同时训练的,AlphaGo先训练策略网络结束后,再训练价值网络(所以不同于Actor-Critic方法的训练模式)。
State-Value Network的训练过程如下:
- 使用两个策略网络进行博弈直到游戏结束(Player v.s. Opponent,Player是Policy Gradient训练后的策略网络,Opponent是Policy Gradient训练中随机选择的某个策略网络),如果agent(Player)赢了,则有: u 1 = ⋅ ⋅ ⋅ = u T = + 1 u_{1}=\cdot\cdot\cdot=u_{T}=+1 u1=⋅⋅⋅=uT=+1否则为: u 1 = ⋅ ⋅ ⋅ = u T = − 1 u_{1}=\cdot\cdot\cdot=u_{T}=-1 u1=⋅⋅⋅=uT=−1
- 计算损失: L = ∑ t = 1 T 1 2 [ v ( s t ; w ) − u t ] 2 L=\sum_{t=1}^{T}\frac{1}{2}[v(s_{t};w)-u_{t}]^{2} L=t=1∑T21[v(st;w)−ut]2
- 梯度下降更新参数: w = w − α ⋅ ∂ L ∂ w w=w-\alpha\cdot\frac{\partial L}{\partial w} w=w−α⋅∂w∂L
有了策略网络和价值网络,AlphaGo的训练就结束了。
Monte Carlo Tree Search
蒙特卡洛树搜索不需要训练,可以直接用于下棋,前面训练的两个网络是为了帮助蒙特卡洛树搜索方法。
首先,我们思考人类在下棋时的行为:
我们发现,人在放下棋子前,总会先设想如果放在这个位置,对手会怎么走,而我下一步又该如何走。所以,我们为了提高胜算,需要让机器能够搜索未来的可能状态(即看得更长远)。
AlphaGo需要搜索未来状态,从中选择胜算最大的那个。下面先了解搜索的主要思想:
- 1.首先选择动作 a a a,该动作不是均匀随机抽样,而是按照概率分布抽样。
- 2.然后让策略网络进行自我博弈(Player v.s. Opponent),看这个动作引起的最后结果是输还是赢;根据胜负和价值函数给该动作 a a a打分;
- 重复1和2多次,选择得分最高的动作。
蒙特卡洛树搜索的具体做法如下,每一轮模拟都分为4步,也就是AlphaGo每下一个棋子都要把以下4步重复很多次:
- 1.Selection:根据策略网络Player的动作得分选择动作 a a a,该动作不会被实际执行,被称为Imaginary action;
- 2.Expansion:模拟对手的动作,即让策略网络Opponent做一个动作,并更新状态;
- 3.Evaluation:根据更新的状态,计算state-value网络的得分 v v v,用于计算动作的action-value;
- 4.Back-up:使用3步中的action-value更新动作得分。
下面进一步详细描述4个步骤的细节,假设当前观测到状态 s t s_{t} st:
1.Selection
首先,对任意的动作
a
a
a计算得分:
s
c
o
r
e
(
a
)
=
Q
(
a
)
+
η
⋅
π
(
a
∣
s
t
;
θ
)
1
+
N
(
a
)
score(a)=Q(a)+\eta\cdot\frac{\pi(a|s_{t};\theta)}{1+N(a)}
score(a)=Q(a)+η⋅1+N(a)π(a∣st;θ)其中,
Q
(
a
)
Q(a)
Q(a)是MCTS中计算出的action-value(初始值为0),
π
(
a
∣
s
t
;
θ
)
\pi(a|s_{t};\theta)
π(a∣st;θ)来自训练后的策略网络,
N
(
a
)
N(a)
N(a)是动作被选择的次数;
η \eta η是超参数需要手动调整。
如果 a a a动作很容易被选中,即 π ( a ∣ s t ; θ ) \pi(a|s_{t};\theta) π(a∣st;θ)过大,但是 N ( a ) N(a) N(a)也会增大,可以平衡数值,避免在 s t s_{t} st下某个动作陷入重复探索导致模型不够灵活。一开始, Q ( a ) = 0 Q(a)=0 Q(a)=0,动作的得分取决于策略网络,随着多次模拟,action-value Q ( a ) Q(a) Q(a)会占据主导地位。
根据当前得分最大者选择动作
a
t
a_{t}
at(深红):
2.Expansion
现在有了
a
t
a_{t}
at,opponent再走一步
a
t
′
a'_{t}
at′将会更新状态为
s
t
+
1
s_{t+1}
st+1;
但是opponent的动作 a t ′ a'_{t} at′应该抽样自: a t ′ ∼ π ( ⋅ ∣ s t ′ ; θ ) a'_{t}\sim\pi(\cdot|s'_{t};\theta) at′∼π(⋅∣st′;θ)此处的状态 s t ′ s'_{t} st′是player下棋后,opponent下棋前的状态。
对于这种设计,其实状态转移函数就与策略函数等价。
我们可以模拟新状态 s t + 1 s_{t+1} st+1如下:
3.Evaluation
在
s
t
+
1
s_{t+1}
st+1的基础上,双方仅进行动作抽样来博弈直到游戏结束,该过程被称为Fast Roll out:
- Player的动作: a k ∼ π ( ⋅ ∣ s k ; θ ) a_{k}\sim\pi(\cdot|s_{k};\theta) ak∼π(⋅∣sk;θ);
- Opponent的动作: a k ′ ∼ π ( ⋅ ∣ s k ′ ; θ ) a'_{k}\sim\pi(\cdot|s'_{k};\theta) ak′∼π(⋅∣sk′;θ)。
如果最后Player赢了,则记录奖励
r
T
=
+
1
r_{T}=+1
rT=+1,否则为
r
T
=
−
1
r_{T}=-1
rT=−1,使用奖励评价状态
s
t
+
1
s_{t+1}
st+1:
另外,还需要用价值网络评价
s
t
+
1
s_{t+1}
st+1:
v
(
s
t
+
1
;
w
)
v(s_{t+1};w)
v(st+1;w);
根据以上两项,得到状态
s
t
+
1
s_{t+1}
st+1的综合评价:
V
(
s
t
+
1
)
=
1
2
[
v
(
s
t
+
1
;
w
)
+
r
T
]
V(s_{t+1})=\frac{1}{2}[v(s_{t+1};w)+r_{T}]
V(st+1)=21[v(st+1;w)+rT]通过Fast Roll out,可以有很多的
s
t
+
1
s_{t+1}
st+1,所以我们可以得到各个状态的综合评价:
因此,每个动作
a
t
a_{t}
at都对应了大量子节点
V
(
s
t
+
1
)
V(s_{t+1})
V(st+1),现在我们要计算的action-value为:
Q
(
a
t
)
=
m
e
a
n
(
V
(
s
t
+
1
)
)
Q(a_{t})=mean(V(s_{t+1}))
Q(at)=mean(V(st+1))
4.Back-up
将action-value更新回对应动作
a
t
a_{t}
at的得分上:
s
c
o
r
e
(
a
t
)
=
Q
(
a
t
)
+
η
⋅
π
(
a
t
∣
s
t
;
θ
)
1
+
N
(
a
t
)
score(a_{t})=Q(a_{t})+\eta\cdot\frac{\pi(a_{t}|s_{t};\theta)}{1+N(a_{t})}
score(at)=Q(at)+η⋅1+N(at)π(at∣st;θ)
模拟结束后的动作决定
经过上面4个步骤的多次模拟,可以得到一组数据:每个动作 a a a以及其被选择过的次数 N ( a ) N(a) N(a);
因此在最终执行动作时,我们只需选择最大次数者作为 a t a_{t} at即可: a t = a r g m a x a N ( a ) a_{t}=argmax_{a}N(a) at=argmaxaN(a)