第 10 回:AI設計入門

インタラクティブ・ゲーム制作
<プログラミングコース>
第10回
AI設計入門
(最終課題アナウンス)
先週は本当にごめんなさい
• ご覧の有様です
• 私が身体を張って皆さんに伝えたいのは
次の2つ
– カルシウムは大事
– 焦るとあんまりいいことない
授業の再リスケジュール
• 海外出張キャンセル
– 海外でこの足はね…
– なので当初の予定通り
• Kinectを来週に
• ラスト2回前は、
AIにも使えそうな
ところを中心に
• 最終回で対決
11.AI設計入門
12.Kinect体験
13.Boostと数学
14.オセロAI対決
今日の内容
• AIの作り方を考えていく
– コーディングよりも考え方メイン
– 雑魚AIを試しに作ってみる
今回のプロジェクトの変更点
• 決着が付くようになっている
– それに伴いいくつか関数追加
– 先々週ライブコーディングした内容の反映
• 盤面の状況そのものを表すデータを
BoardInfoクラスに分離
– AI実装を見越しての変更
まずは考え方から
AI設計入門
AI(人工知能)
• 本当はゲームの思考ルーチン程度を
人工知能呼ばわりすると怒られる
• 特定の選択肢の中からそれっぽい選択や
行動をするもの、をAIと呼ぶことにする
– 確率によって適当な選択をするもの
– 選択肢に対するリスクやリターンを考えて、
選択をするもの
そもそも選択肢とは
• トランプや将棋のような思考AI
– 手番単位で進行していくので分かりやすい
– 完全情報ゲームに分類される
• もっと言うと二人零和有限確定完全情報ゲーム
• アクションゲームなどの場合
– フレーム単位での選択肢はキー操作
• だがキー操作単位で行動制御すると不審な挙動に
– 戦術・戦略レベルでの状態によって管理
まずは選択肢を列挙しよう
• これをしないと打てないところに
打とうとするクソAIになってしまう
– 幸い、前回の時点でBoard::isPuttable()
という関数は作ったので、これを利用したい
• まずは実装
まずは初級編
今の状態だけで判断する
選択肢が列挙できたので…
1. とりあえず最初の選択肢を選ぶ
– 思考放棄型その1
2. 適当に選ぶ
– 思考放棄型その2
•
•
だが、何となく人間味は出る
そして超級に通じる方法だったりする
3. 端っこが取れそうなら取りたい
– 多少強くなる、かもしれない
乱数の使い方
• srand()で種を初期化
– その時点での時刻を使うのが一般的
• srand((unsigned int)time(NULL));
• rand()が0~RAND_MAXの値を返す
– 実数にキャストして0.0~1.0の値にする
– もしくは%演算子で好みの範囲の値にする
• ただし、バラツキが出るようになるので注意
• もっといい乱数が必要な場合
– メルセンヌ・ツイスター法などを利用
中級~上級といったところ
先読みして判断する
実際に置いたらどうなるか
考えて手を決める
1. 一番たくさんひっくり返せる手
– 目先の欲を追う型
2. 次の自分の番で選択肢が一番多くなる手
– オセロのセオリーにのっとる型
• 特に2.では「相手の手を推測する」という
ロジックが必要になるので、
これをどうしようか?
ミニマックス法
(ネガマックス法とも)
• 取り得る選択肢に評価点を付けて、
自分に有利、相手に不利になるような
選択肢を選ぶ
– 評価基準は、個数か、置ける場所数か、
あるいはその複合かで好きに選ぶ
• これなら数手先まで深読みが可能
超級
賢くはないが、腕尽くで
モンテカルロ法
• 乱数でシミュレーションを進める総称
• オセロの場合
– ある手を打つ
– その後勝負が付くまでお互いランダムに打つ
– これを数百回~数千回繰り返し、手ごとに
勝率を出す
– 一番勝率の高い手を採用する
最終回にむけて
ルール確認
ルール(1)
• 来週月曜に対決用プロジェクトを公開
• AIBaseクラスを継承し、
自分のアルゴリズムを実装
– それ以外のファイルには手を加えては
いけない
– getHand()で渡されてくる情報以外は
参照禁止
– 1手の計算に使える時間は30秒まで
• 私のMBAでの経過時間基準
ルール(2)
• 難易度は4段階用意
– 自分に合った難易度で挑戦してね!
– Sチャレンジができるのは最高難易度
• 漏れなくライブで実況します
• 提出期限は7/23(火)23:59まで
– 組み込みチェックなどが必要なので、
それ以降は受け付けません
TO BE CONTINUED…