京都大学艦これ同好会 会員の雑記ブログ

京都大学艦これ同好会は、艦これを通じてオタクとの交流を深める緩いコミュニティです。普段はラーメンを食べています。

機械学習を使って聯合走者を推定してみた

京艦同のK6です.

なんか時速上がりましたね(しーちゃんありがとう)

Bonodere用の聯合予測アルゴリズムを新環境に対応させるついでにやり方も変えました.

興味のある方もいるかと考え本記事にて軽く紹介します.

概要

始める前にBonodereの聯合予測機能について説明しておきます.

聯合というのは(稀な場合を除き)他の報酬群よりたくさん素戦果を稼がないと入れないものです.順位500位までの提督が入賞できる3群のボーダーは,イベントの有無とその難易度,クオ砲・イヤ砲のリセット月,期間限定戦果砲等でだいたい決まるため,集団的挙動を示します.(非専門なので正しい用語は分かりません).一方,聯合はその月に走っている人物とその人数のみで決まります.他の入賞群は○○稼げば大丈夫やろ・・みたいな感覚で走れますが,聯合は「周りがどうであれD300入れる」とかの人でもなければ,同サーバーの人物を監視することが入賞の前提条件となります.

なので聯合は厳しい"空気読みゲーム"になることが多いです.聯合を常連する提督を事前に把握しておき(もしくは親しくなる),狙っている月が始まったらビュアーのページをめくりながら走っている人物・人数を確認する能力が肝心でした.この作業を簡単にするのがBonodereの聯合予測アルゴリズムです.ある程度素戦果を稼いでいるアカウントが必ず示す特徴を幾つか設定しておき,ある期間中のデータを入力すれば,設定した条件を満たす提督を一瞬で把握できます.

今までは僕が聯合を走りながら学んだ経験則で条件を立てていましたが,完璧とは程遠いアルゴリズムでした.例えば,明らかに戦果砲とEOを撃っているだけのアカウントが聯合走者としてフィルタリングされたり,イベント月だと戦果勢が稼ぐ素戦果が全体的に低く,5人も検出されない場合もありました.

誤検知データの一例

これらの問題を解決するために人工的なif文で成り立っているアルゴリズムではなく,実際のデータから聯合走者らしき挙動を学んでいく機械学習を使うことにしました.ちなみに僕自身は機械学習の初心者なので(所属する研究室ですごいことやっている先輩にちょっと教えてもらっただけ)理論が間違っている/説明がおかしいかもしれません.ご指摘いただければ修正します.

機械学習とは

機械学習というと何かすごい技術に聞こえるかもしれませんが,やっていることはエクセルでやるデータの線形回帰と原理的に違いはありません.極端に簡単な例を挙げて,何らかの予測を行うニューラルネットが以下のデータを学習したとしましょう.

「入力  x=x_Aに対する出力は  y=y_A

「入力  x=x_Bに対する出力は  y=y_B

「入力  x=x_Cに対する出力は  y=y_C

「入力  x=x_iに対する出力は  y=y_i

「...」

モデル  y=M(x)に十分な自由度があるとすると,学習を完了したモデルは学習させたデータに対し正しい答えを出力します.

 y_i=M(x_i)\,,\hspace{0.5cm}i=A,B,C,...

さらに,学習したことがないデータ点  x=x_Dが与えられても,モデルは学習に使ったデータに基づいて一番可能性が高いとされる出力  y=y_Dを出します.これが可能になる原理をこれから説明します.

機械学習に使われるニューラルネット(特にFeedforwardネットワーク)は一般に次の形で記述されます.

 s_{k+1}=\phi_k(W_ks_k+b_k)\,,\hspace{0.5cm}k=1,2,...,K

ここで  s_kは各レイヤーの値, \phi_k(\cdot),\,W_k,\,b_kは各レイヤーの活性化関数(何かの非線形関数),重み,バイアス(行列とベクトル)を表します.各レイヤーは  n_k個のニューロンを持ち,前後のニューロンと上式で繋がれています.その構造は生物のニューロンと似ているため,このような関数はニューラルネットと呼ばれています.ニューラルネットは入力を  s_1=xとして取り,K個のレイヤーを通して演算が行われ,結果 y=s_{K+1}が出力されるので,学習を終えて実際に使うときは「予測を行う関数」として考えることができます.

ニューラルネットワークWikipedia

ニューラルネットは学習の際,重みとバイアス  W_k,\,b_kを適切に調整していき,学習データ  (x_i,y_i)\in\mathcal{D}に対する誤差  L(\mathcal{D};w)(ロスと呼ばれる)を最小化していきます.

 L(\mathcal{D};w)=\sum_{i\in\mathcal{D}}\|M(x_i;w)-y_i\|^2

また,過学習を防ぐために正則化項を導入することもあります.

 L(\mathcal{D};w)=\sum_{i\in\mathcal{D}}\|M(x_i;w)-y_i\|^2+r\|w\|^2

上式で  wは重みとバイアス  W_k,\,b_kの全成分を一つのベクトルに表したものです. r正則化の強度を調整するパラメータとなっています.これらのロスは一般的に勾配法やその変形法で最小化(ニューラルネットの訓練)していきます.

 w_{j+1}=w_{j}-\alpha_k\frac{\partial L}{\partial w}\bigg|_{w=w_j}

 \alpha_jは学習時間  jでのステップサイズ, \frac{\partial L}{\partial w}はロスに対する重みとバイアスの勾配となっています.勾配はロス  L(\mathcal{D};w)が増加する最急方向を向くため,その反対方向へ  wを更新するとロスが減少し,学習するデータに対し正しい結果  y_i\approx M(x_i)を出力するようになります.

聯合予測に使うニューラルネットは以下の入出力関係を持ちます.

  • 入力:14個(1週間)の戦果増分
  • 出力:聯合走者である確信度0~9

例えば入力 \lbrack 14, 3, 36, 6, 20, 4, ...\rbrack^{\top}に対する出力は  0,入力  \lbrack 250, 89, 274, 97, 247, 90, ...\rbrack^{\top}に対する出力は  9であってほしいですね.また,このニューラルネットが出力する結果は  0\sim 9の連続的な値を持つため,Bonodereの利用者はある感度  y_sを設定し, M(x)\geq y_sとなるアカウントをすべてフィルタリングすることで任意の数の聯合走者を入賞の可能性が高い順で表示することができます.

学習データの取得

訓練用データの作成環境はSavara氏が構築してくれました.だんけだんけ

当時のチャット

訓練用データの生成(人力)

学習データは多ければ多いほど予測の精度が良好になると考えられますが,途中で飽きたのでとりあえず4000点生成しました.

今後もデータ点を増やしていくつもりです.

モデルの訓練

ニューラルネットの構造(レイヤーの数と各レイヤーにおけるニューロンの数)および正則化パラメータ  rはグリッドサーチを使って最適化することができますが,alpha版には適当に決めて隠れ層を2枚,各層のニューロンは10個,5個を利用しました.

alpha版の構造

訓練の結果

学習データ4000個でもかなり精度の高い予測ができていたので,当初の目標であったデータ点1万からなるニューラルネットはまた今度組んでみることにしました.

実際のデータで検証

Bonodereへの導入

学習が終わったニューラルネットの重みとバイアス  W_k,b_kをすべて取り出し,Bonodere内のコードで関数を再現するだけです.(こちらはSavara氏が担当)

2024年10月のタウイ上位3人(classification点数が高い)

おわりに

アルゴリズムの構築に協力していただいた皆様に感謝します.学習データの生成作業が虚無すぎるのでやってみたい方いらっしゃいましたらご連絡ください.