TadaoYamaokaの開発日記

個人開発しているスマホアプリや将棋AIの開発ネタを中心に書いていきます。

将棋でディープラーニングする その8(出力に移動元を追加)

前回までのニューラルネットワークでは、差し手の移動先のみを出力して、移動元については考慮していなかった。
移動元をどのように出力するかは悩んでいたのでとりあえず移動先のみで検証を行った。

移動元クラス数:盤のマス数(9×9)+持ち駒の種類(7)
移動先クラス数:駒の種類(14)×盤のマス数(9×9)
であるため、
移動元と移動先の組み合わせると、(9×9+7) × (14×9×9) = 642978 のクラス分類となる。

分類数が増えすぎると精度を上げるのは難しいので、移動元を移動先と別々に出力することを考えていた。

こちらの方も別々に出力している。
http://www2.computer-shogi.org/wcsc27/appeal/GANShogi/wcsc27.pdf

しかし、移動元を移動先と別々に出力すると、移動元と移動先が矛盾した結果になる可能性がある。
また、指し手のオーダリングする際、上位数手を使用すると、移動元と移動先を組み合わせて使用する必要があり、それは出力で考慮できていない。

というように悩んでいたが、解決方法が見つかった。
といっても自分で発見したわけではなく、こちらの方が昨日公開したソースの実装方法が参考になった。

この実装では、移動元を移動方向で表現している。
移動元から移動先への方向が分かれば、どの駒を移動したかを一意に決めることができる。
自分では気づきませんでした。素晴らしいアイディアです。

上記の実装では、移動方向を10方向(8方向+桂馬の動き)と成りと持ち駒で分類している。
よって、分類クラス数は(10×2+7)×9×9 = 2187となる。
どの駒を移動したかは移動方向からロジックで一意に決まる。

参考にして、前回までの指し手の駒の種類は残して、移動方向を加えることにした。
移動方向のみの方が分類数は減らせるが、駒の種類を残すのは、駒の種類は指し手の意味として重要な情報なので残した方がよいだろうと考えたためである。
どちらがよいかは実験してみないとわからない。

駒の移動は、以下を考慮して分類数を減らす。

  • 駒ごとに移動できない方向がある
  • 持ち駒にならない駒がある
  • 成れない駒がある

駒ごとの移動できる方向を考慮すると、下記表の〇の個所のみに絞られ、分類数は71となる。

左上 右上 左下 右下
と金
成香
成桂
成銀
竜馬
竜王

また、成りができるのは上記表の「飛」までなので、方向と成りの組み合わせで分類数は、71+23=94となる。
また、持ち駒にできるも上記表の「飛」までなので、方向と成りの組み合わせと持ち駒の合計で、分類数は94+7=101となる。
これと、盤の位置の組み合わせで、最終的な分類数は101×9×9 = 8181となる。

これくらいの分類クラス数であれば、それなりの精度になりそうである。
クラス数が絞られることで、予測した指し手が合法手になる確率も上がる。
また、移動元が一意に決まるため、そのままオーダリングに使用可能である。

測定結果

前回のコードに移動元(移動方向)の考慮を出力に加えて、測定を行った。
測定方法は、前回までと同様、プロの棋譜422852局面で3エポック学習した。

train loss test accuracy
移動元考慮なし 2.09 0.40
移動元考慮あり 2.15 0.41

分類クラス数が増えているが、移動元(移動方向)を考慮してもほぼ同じ精度で予測できている。

学習時間は以下の通り少しだけ増えた。

学習時間
移動元考慮なし 0:47:34
移動元考慮あり 0:49:15

GitHubソースコードを公開しました。
github.com