質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.48%
C#

C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

Q&A

解決済

2回答

1619閲覧

コマンドRPGの戦闘場面で味方敵素早さ順で交互に行動させたい

gemfighter

総合スコア38

C#

C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

0グッド

0クリップ

投稿2020/02/24 02:46

C#

1public abstract class Status : MonoBehaviour 2{ 3 public string Name { get; set; } //名前 4 public int Level { get; set; } //レベル 5 public int HP { get; set; } //体力 6 public int Max_HP { get; set; } //体力最大値 7 public int MP { get; set; } //マジックポイント 8 public int Max_MP { get; set; } //マジックポイント最大値 9 public int ATTACK { get; set; } //攻撃力 10 public int DEFENCE { get; set; } //防御力 11 public int SPIRIT { get; set; } //精神力 12 public int SPEED { get; set; } //素早さ 13 public bool Living { get; set; } //生存フラグ 14 public string Image { get; set; } //画像の名前 15 16} 17 18public class Chara : Status 19{ 20 //こんすとらくた  21 public Chara(string name, int lv, int hp, int mp, int at, int df, int sp, int spd, string image) 22 { 23 Name = name; 24 Level = lv; 25 HP = hp; 26 Max_HP = HP; 27 MP = mp; 28 Max_MP = MP; 29 ATTACK = at; 30 DEFENCE = df; 31 SPIRIT = sp; 32 SPEED = spd; 33 Living = true; 34 Image = image; 35 } 36} 37 38public class MoveController : MonoBehaviour 39{ 40 public static Chara[] Player = new Chara[4]; 41 public static Chara[] Teki = new Chara[2]; 42 43 void Start() 44 { 45 this.rigidBody = GetComponent<Rigidbody2D>(); 46 // 衝突時にobjectを回転させない設定 47 this.rigidBody.constraints = RigidbodyConstraints2D.FreezeRotation; 48 49 //インスタンス 50 Player[0] = new Chara(" ", 1, 100, 15, 15, 15, 10, 5, " "); 51 Player[1] = new Chara(" ", 1, 120, 20, 15, 10, 20, 10, " "); 52 Player[2] = new Chara(" ", 1, 100, 10, 10, 10, 10, 15, " "); 53 Player[3] = new Chara(" ", 1, 90, 30, 0, 5, 30, 5, " "); 54 55 56 Teki[0] = new Chara(" ", 1, 10, 4, 1, 1, 10, 5, " "); 57 Teki[1] = new Chara(" ", 10, 1000, 10, 10, 10, 10, 5, " "); 58 59 } 60}

上記のコードは今作っているRPGのステータスです。
現在戦闘場面で、どうやって味方敵素早さ順で交互に行動させようか悩んでいます。

一応、ソート順でやろうかなと考えていますが、どうやって異なるインスタンスを組み合わせてソート順(素早さを)に並べるか方法が分かりません。

どなたか助言をお願います。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

YAmaGNZ

2020/02/24 11:49

敵味方交互の順番にするのであれば、2つの配列をマージする必要がなさそうに思えます。 提示されている例だと、順番は Player[2]→Teki[0]→Player[1]→Teki[1]→Player[0]→Player[3] ということですか? それとも、ターン関係なく常に敵味方が交互ということで Player[2]→Teki[0]→Player[1]→Teki[1]→Player[0]→Teki[0]→Player[3]→Teki[1] ということですか? そうではなく、敵味方を完全にマージしてSpeed順にするということですか? また、Speedが同じ値の場合はその中でどうやって順番付けするのでしょうか?
gemfighter

2020/02/24 12:35

敵味方を完全にマージしてSpeed順で、 Player[3]→Player[2]→Teki[0]→Player[1]→Teki[1]→Player[0]という風に考えています。 スピードが同じ場合はまだ考えていないです。
YAmaGNZ

2020/02/24 13:09

Speedはコンストラクタの最後から2つ目の引数だから、Player[3]はSpeed=5なのでは? また、Speedが同じ場合は考えていないとのことですが、Speed=5のキャラクターが4ついて、明らかに順番をつけているように見えますがどのような基準で順番をつけているのでしょうか?
gemfighter

2020/02/24 13:16

すみません! 間違えました! Player[2]→Player[1]→Teki[0]→Player[0]→Teki[1]→Player[3] です!
guest

回答2

0

ベストアンサー

配列のマージに関しては、Enumerable.Concat<TSource>IEnumerable<TSource>, IEnumerable<TSource>) メソッドを利用されるなど方法はいくつかあります。
「C# 配列 マージ」などで検索すればよろしいかと思います。

また、配列のソートに関しても「C# 配列 ソート」と検索すれば方法はいろいろ出てくるかと思います。

C#

1Chara[] total = Player.Concat(Teki).OrderBy(a => -a.SPEED).ToArray();

2つを組み合わせるとこんな感じになります。

ただ、この方法ですと、2つの配列をマージして、Speedの降順でソートしているだけですので質問への追記・修正のコメントにあるような順番で並ぶわけではありません。

投稿2020/02/24 13:32

YAmaGNZ

総合スコア10258

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

gemfighter

2020/02/25 08:21

OrderByの中のaは何を指していますか?
YAmaGNZ

2020/02/25 08:43

OrderByの中はラムダ式と呼ばれる書き方です。 aは入力されるパラメータとなり、今回の場合はマージした配列の各要素となります。 OrderByにてソートしようと各要素を比較しようとした時にa => -a.SPEEDが実行されることになります。 これは、ソートに使う値として、各要素のSpeedのマイナス値を使いますよということになります。 何故マイナス値かというと、OrderByだと昇順に並べますので、マイナス値にすればもともとの値が大きいほど小さい数字になりますので、昇順で並べると逆順となり結果的に降順となります。 また、OrderByDescending(a => a.SPEED)としても同じです。
gemfighter

2020/02/25 14:20

では、aのところはxでもyでも大丈夫ですか?
YAmaGNZ

2020/02/25 14:25

変数名として使用できるものであれば何でも大丈夫です。 1文字限定という訳でもありませんので 例えば OrderBy(item => -item.SPEED) でもかまいません
guest

0

C#

1//インスタンス 2Player[0] = new Chara(" ", 1, 100, 15, 15, 15, 10, 5, " "); 3Player[1] = new Chara(" ", 1, 120, 20, 15, 10, 20, 10, " "); 4Player[2] = new Chara(" ", 1, 100, 10, 10, 10, 10, 15, " "); 5Player[3] = new Chara(" ", 1, 90, 30, 0, 5, 30, 5, " "); 6 7 8Teki[0] = new Chara(" ", 1, 10, 4, 1, 1, 10, 5, " "); 9Teki[1] = new Chara(" ", 10, 1000, 10, 10, 10, 10, 5, " ");

私ならこの時点で一度、構造体の配列を作ってしまいますね。

C#

1Status character[6]; 2 3character[0] = new Status (" ", 1, 100, 15, 15, 15, 10, 5, " "); 4character[1] = new Status (" ", 1, 120, 20, 15, 10, 20, 10, " "); 5character[0] = new Status (" ", 1, 100, 10, 10, 10, 10, 15, " "); 6character[0] = new Status (" ", 1, 90, 30, 0, 5, 30, 5, " "); 7character[0] = new Status (" ", 1, 10, 4, 1, 1, 10, 5, " "); 8character[0] = new Status (" ", 10, 1000, 10, 10, 10, 10, 5, " "); 9 10for(int i = 0; i < 4; i++){ 11 Player[i] = new Chara(character[i]) 12} 13 14for(int i = 0; i < 2; i++){ 15 Teki[i] = new Chara(character[i + 4]) 16}

こうすることで、敵味方の関係ない、characterのデータを作ることが可能です。
これで異なるインスタンスでも一体化することが出来ました。

投稿2020/02/24 03:16

stdio

総合スコア3307

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問