知っておくと便利な使い方

ここでは、知っておくと便利な具体的な使い方をご紹介します。

[紹介する内容]

(1) 現在地を中心とした5×5マスのマップ情報を取得
(2) ゴールを目指して移動する
(3) 草薙剣の場所を確認する
(4) 配列に含まれる座標の数を確認する
(例:経路検索した経路があるかを確認する)
(5) ゴールの1マス手前にトラップアイテムを置く
(6) 一番近い加点アイテムを目指して移動する
(7) ターン数を管理する
(1) 現在地を中心とした5×5マスのマップ情報を取得

  • 下のブロックを組み合わせて使用することにより、現在地を中心とした5×5マスのマップ情報を取得できます。

[参考]

  • スモウルビー甲子園で用意した命令ブロックは、ジャンル「甲子園」の中に入っています。
  • また、ジャンルとブロックの色は一緒になっていますので、色を参考にブロックを探すこともできます。
  • よく使う関数ブロックや文・式ブロックは次のジャンルに入っています。

(2) ゴールを目指して移動する

  • 経路検索ブロックは、引数を省略すると(始点・終点・通らない座標を未指定)、現在地からゴールまでの最短経路を検索します。

  • 経路探索ブロックを変数ブロック「セット 宛先」に組み込み、名前を付けます。
    (名前は自由に付けることができます。ここでは「route」とします。)
    名前を付けることにより、経路検索の結果を後から利用できます。

  • 移動ブロックの中に式ブロックを組み込み、移動先として「route[1]」を入力します。

  • 「route[1]」は、経路検索の結果「route」の指定番号1を指定するものです。
    始点を現在地としている場合、移動できるのは隣接する1マスですので、次の移動先は指定番号の1になります。
    例)経路検索で、[[8,11][8,10][8,9][8,8][7,8][7,7]]が返された場合

  • 経路検索の結果と移動ブロックを組み合わせることにより、出来上がりです。

    [ブロックの処理内容]

    • 経路検索を実施(始点:現在地、終点:ゴール、通らない座標:未設定
    • 経路検索の結果に名前「route」を付ける
    • 変数「route」の指定番号1を移動先として移動する
(3) 草薙剣の場所を確認する

  • 下のブロックを使うと、マップ探索で取得したマップ情報から指定したマップ要素やアイテムの座標を呼び出すことができます。

  • 30点と40点の加点アイテムの座標を確認したい場合は、地形・アイテムは次のように指定します。
    (加点アイテムの値 丁銀30点:c、シロイルカ40点:d)

    [使用例]

    ▶水たまりの場合 
    ▶加点アイテム全部の場合 
    ▶シロイルカ(加点アイテム40点)の場合 
    ▶減点アイテム全部の場合(引数未指定)
    ▶爆弾(減点アイテム40点)の場合 

    =>引数は配列で指定するため、必ず[ ]の中に指定したい値を入力してください。
       また、文字の場合は””を必ず付けてください。

    =>指定できるマップ要素、アイテムの種類と値とは次のとおり

    =>引数を省略した場合は減点アイテム4種類の場所が返されます。

    [アイテム等の種類と値]

  • 変数ブロックに、要素確認ブロックを組み込み、名前「kusanagi」を付けます。
    (名前は自由に付けられます。)
    これで後からこの情報を使用することができます。

    [注意]

    • マップ探索を実施したエリアの情報のみが確認できます。
      (マップ探索をしていないエリアの情報は確認できません。)
    • また、確認できる情報はマップ探索を行った時点での情報です。
      アイテムを対戦相手が取得してなくなっているなど、情報が古くなっている場合がありますので、注意してください。
(4) 配列に含まれる座標の数を確認する
(例:経路検索した経路があるかを確認する)

  • Rubyのlengthメソッドを使用することにより、配列に含まれる座標の数を確認することができます。(lengthメソッドでは、指定した配列に含まれる要素の数を返します。)
  • 例えば、経路検索では、指定した条件の経路がない場合は、始点の座標を1つだけ返します。このことから、lengthメソッドを使うことにより、経路のありなしを確認できます。(戻り値が1の場合は経路がないことが分かります。)
    また、lengthメソッドを使って、加点アイテムの有無なども確認できます。

    [使用例]

    “減点アイテムを避けてゴールする経路を検索し、もし、この経路がない場合は、ゴールまでの最短経路を検索する”

    [ブロックの処理内容]

    • 減点アイテムの座標を確認し、その結果に「traps」と名前を付ける
    • 始点:現在地、終点:ゴール、通らない座標:減点アイテムで、経路を検索し、その結果に「route」と名前を付ける
    • もし、「route」に含まれる座標の数が1であれば(経路がない場合は)、始点:現在地、終点:ゴール、通らない座標:未設定で経路検索する
(5) ゴールの1マス手前にトラップアイテムを置く

  • lengthメソッドを使って、ゴールの1マス手前かどうかを判定することができます。
    経路検索の結果は、現在地からゴールまでの経路順の座標が返されるので、ゴールの1マス手前では、現在地とゴールの2つの座標が返されます。よって、length=2の場合が1マス手前になります。

  • このブロックを条件分岐ブロックに組み込みます。

  • 続いて条件分岐ブロックの中に、条件が真の場合の処理を組み込みます。
    ここでは「トラップアイテムを置く」と「移動」ブロックを組み込みます。
    これで完成です。

    [ブロックの処理内容]

    • 現在地からゴールまでの最短経路を検索し、その結果に「route」という名前を付ける。
    • 「route」に含まれる座標の数が2かどうかを判定する。
    • 真(座標数が2)の場合は、トラップアイテムを現在地に置き、移動(ゴール)する。
    • 偽(座標数が2以外)の場合は、次の処理に進む。
(6) 一番近い加点アイテムを目指して移動する

  • マップ上の指定した要素(アイテムマップ要素)の座標を確認する方法は(3)でやったとおりですが、今度はマップ上の加点アイテムの座標を確認し、一番近い加点アイテムを終点として移動するブロックを作ります。
  • 最初に加点アイテムの座標を確認し、この結果に「items」という名前を付けます。

  • 次に「items」に含まれる座標を現在地から近い順に並べ替えます。
    (「items」に含まれる座標は、y軸の座標数が小さい順に並んでいます。)
    この処理を「sort_by!」「calc_route」「size」メソッドを使って行います。
    sort_by! ブロックを使って配列に含まれる要素をソートし、配列自身を変更するメソッドです。ブロック引数に配列に含まれる各要素を入れながらブロックを繰り返し実行し、ブロックの戻り値を集めます。集めた戻り値を<=>演算子で比較して、小さい順に要素を並べます。

    配列.sort_by!{|変数| ブロック(ブロック引数)}

    例)
    animals = [“mouse”, “cat”, “elephant”, “lion”]
    animals.sort_by! {|animal| animal.size }
    ※ .sizeメソッドは文字数を返します。
    =>配列の中身が次のように小さい順に並べ替えられます。
    animals = [“cat”, “lion”, “mouse”, “elephant”]
    calc_route スモウルビー甲子園で用意した2点間の最短経路を検索するメソッドです。(下のブロックと同じ内容です。)

    引数として始点(src)、終点(dst)、通らない座標(except_cells)を指定できます。
    なお、引数を省略した場合は、始点:現在地、終点:ゴール、通らない座標:未設定で経路検索します。

    calc_route(src:配列,dst:配列,except_cells:配列)

    例)
    calc_route(src:[11,8],dst:[7,7],except_cells:[9,9])
    =>次のような経路順の座標配列が返されます。
     [[11,8],[11,7],[10,7],[9,7],[8,7],[7,7]]
    size 配列の要素の数を返します。

    配列.size

    例)
    numbers = [1,2,3,4,5]
    numbers.size
    =>4
  • 上で説明した「sort_by!」「calc_route」「size」メソッドを次のように組み合わせます。

    [処理内容]

    • 「items」に含まれる加点アイテムの各座標に「item」という変数を設定
    • calc_routeを繰り返し実行(「item」(加点アイテム)が5つであれば5回繰り返す)
        始点:現在地
        終点:item(「items」に含まれる各加点アイテムの座標)
        通らない座標:未設定
    • 「item」の各戻り値の座標数(要素数)を求める
    • この座標数が少ない順に「items」の中の座標を並べ替える
       ※calc_routeは経路順の座標を返すので、座標数が少ない=現在地から近いになる
  • 次に一番近い加点アイテムを終点として設定できるよう「items」に含まれる先頭の座標に「target」という名前を付けます。

    firstメソッドは、配列の最初の要素を返します。
    items.firstでは、「items」の先頭の座標を返します。

  • 一番近い加点アイテムを取得すると、次に近い加点アイテムを目指して移動する必要があります。
    この処理を正しく行うためには、マップ情報を新しくし、「items」の情報を更新していく必要があります。
    このため、この一連のブロックの先頭にマップ情報の取得ブロックを組み込んでおきます。
    =>これにより、ターンのたびに、まずは現在地周辺のマップ情報を取得し、「items」の情報が更新されます。
    =>ただし、情報が更新されるのは現在地周辺(5×5マス)だけのため、この範囲外で対戦相手が加点アイテムを取得した情報は取得できません。

  • 最後に「first_item」を終点に設定して移動するブロックを組み込んで完成です。

(7) ターン数を管理する

  • 1ターンの行動として、AIプログラムの「◆ずっと  を繰り返す」の中のプログラムが1回実行されます。よって、「◆ずっと  を繰り返す」の実行回数がターン数と同じ数になります。
    このことから、「◆ずっと  を繰り返す」が実行された回数を変数設定することによりターン数を管理することができます。
  • 最初に「◆ずっと  を繰り返す」より前に「turn = 1」を設定します。
    (これで最初のプログラム実行は「turn = 1」としてスタートします。)

  • 次に「ターンを終了する」の前に「turn = turn + 1」を組み込みます。
    (ターン終了時に「turn」に1を加えることにより、ターン数が加算されていきます。)

  • ターン数を管理することにより、次のようにターン数毎の行動をプログラムすることができます。

クリエイティブ・コモンズ・ライセンス

このドキュメント は クリエイティブ・コモンズ 表示 4.0 国際 ライセンス の下に提供されています。