i-school - switch文とif文の使い分け方とその実装例
 具体的なゲーム内の処理を例に、switch文とif文の使い分けを解説します。

 両方の記述について掲載しますが、より適している記法を先に提示します。



1.キャラクターの状態に応じたアニメーションの切り替え


 ゲーム内のキャラクターが、走っている状態、ジャンプしている状態、攻撃している状態といった複数の状態を持っているとします。

 これらの状態に応じて適切なアニメーションを表示したいとき、enumとswitch文を使うとコードがきれいにまとまります。


<switch 文の場合>


// enumでキャラクターの状態を定義
public enum CharacterState {
    Running,
    Jumping,
    Attacking
}

// キャラクターの状態
CharacterState state = CharacterState.Running;

// switch文を使って、状態に応じたアニメーションを再生
switch (state) {
    case CharacterState.Running:
        // Runningのアニメーションを再生
        break;
    case CharacterState.Jumping:
        // Jumpingのアニメーションを再生
        break;
    case CharacterState.Attacking:
        // Attackingのアニメーションを再生
        break;
    default:
        // 未定義の状態の場合の処理
        break;
}


<if 文の場合>


 以下のようにif文を使用しても同じように処理できますが、switch文を使う方が可読性が高いです。
特に、状態が更に増える場合、if文では複雑さが増してしまいます。

CharacterState state = CharacterState.Running;

// if文で書き直す
if (state == CharacterState.Running) {
    // Runningのアニメーションを再生
} else if (state == CharacterState.Jumping) {
    // Jumpingのアニメーションを再生
} else if (state == CharacterState.Attacking) {
    // Attackingのアニメーションを再生
} else {
    // 未定義の状態の場合の処理
}



2.敵キャラクターのAI行動


 敵キャラクターがプレイヤーの距離に応じて行動を変える場合、if文が便利です。
距離が10m以下なら攻撃、20m以下なら接近、それ以上なら待機といった具体的な範囲に基づいた条件を設定できます。


<if 文の場合>

float distance = // プレイヤーとの距離

// if文を使って、距離に応じた行動を選択
if (distance <= 10) {
    // 攻撃する
} else if (distance <= 20) {
    // 接近する
} else {
    // 待機する
}


<switch 文の場合>


 以下のようにswitch文を使用しても処理は可能ですが、可読性も悪く、範囲に基づく条件判断が難しくなるため、この場合はif文の方が適しています。

float distance = // プレイヤーとの距離

// switch文で書き直す(非推奨)
switch (distance) {
    case var d when d <= 10:
        // 攻撃する
        break;
    case var d when d <= 20:
        // 接近する
        break;
    default:
        // 待機する
        break;
}


3.イベント発生時の処理


 ゲーム内の特定のイベント(たとえば、プレイヤーが宝箱を開ける、敵を倒すなど)が発生したときに、それぞれ異なる処理を行いたい場合、switch文が適しています。

 設定されている範囲が事前に決まっている場合には、やはり、enum との組み合わせが効果的です。


<switch 文の場合>


// enumでイベントの種類を定義
public enum GameEvent {
    OpenChest,
    DefeatEnemy,
    ReachGoal
}

// ゲームイベント
GameEvent gameEvent = GameEvent.OpenChest;

// switch文を使って、イベントに応じた処理を実行
switch (gameEvent) {
    case GameEvent.OpenChest:
        // 宝箱を開ける処理(アイテムを獲得する等)
        break;
    case GameEvent.DefeatEnemy:
        // 敵を倒す処理(経験値を得る等)
        break;
    case GameEvent.ReachGoal:
        // ゴールに到達した処理(レベルクリア等)
        break;
    default:
        // 未定義のイベントの場合の処理
        break;
}


<if 文の場合>


 以下のようにif文を使用しても処理できますが、switch文の方が綺麗にまとまり、また値の範囲が限定されるため、読みやすさとバグの発生を防ぐ点で優れています。

GameEvent gameEvent = GameEvent.OpenChest;

// if文で書き直す
if (gameEvent == GameEvent.OpenChest) {
    // 宝箱を開ける処理(アイテムを獲得する等)
} else if (gameEvent == GameEvent.DefeatEnemy) {
    // 敵を倒す処理(経験値を得る等)
} else if (gameEvent == GameEvent.ReachGoal) {
    // ゴールに到達した処理(レベルクリア等)
} else {
    // 未定義のイベントの場合の処理
}


4.switch文とif文の使い分けのポイント


 これらのケースように、switch文とif文はそれぞれ異なる状況において優れた読みやすさパフォーマンスを提供することが目的です。

 先ほどのサンプルコードを念頭に置いて、それぞれの特徴を見直してみましょう。



 switch文は、ある変数が特定の値を持っているかどうかを繰り返し確認する必要がある場合に便利です。
特に、この変数の値があらかじめ限定された範囲内(セット)にあることが分かっている場合(例:キャラクターの状態やゲームイベントなど)には、enumと一緒に使うと非常に効果的です。

 このセットがあらかじめ知られていて、それらの選択肢が相互に排他的である場合、switch文はコードをきれいに保つのに役立ちます。それはまた、ある変数が取りうる値を見つけやすくするため、バグを見つけるのに役立つ可能性があります。



 一方、if文は、一連の条件を順番に確認し、最初に真となる条件に対応する処理を実行したい場合に便利です。
変数が特定の範囲内にあるかどうかを確認する場合(例:敵キャラクターのAI行動など)には、if文が自然にフィットします。

 特に、連続的な範囲または条件が重複する可能性がある場合に有用です。
異なる範囲に跨る条件を扱うことが可能であり、それがswitch文の場合には記述が困難になります。


5.まとめ


 switch文とif文の使い分け方の実装例を提示しました。
それぞれのポイントを理解いただければ幸いです。

 最終的には、使いやすさ、コードの可読性、そしてあなたがどの程度の精度で条件を制御したいかによります。
両者の違いを理解し、自身のニーズに最適な選択を行うことが重要です。

 どちらの方が適しているかは、実際に自分で両方のケースを書いてみながら使い方を習得していくことをお勧めします。