関連記事
条件分岐はif文、switch文を使い分けろ!
この記事の動画版はこちら(画像クリックでYoutubeに飛びます)
今回は、プログラミングの「条件分岐処理」についてご説明します。
条件分岐処理は、ループ処理と並んで「プログラミングには無くてはならないもの」です。
前回のループ処理の記事では「ループ処理はWebサービス全体のソースコードの8~9割には登場する」と紹介しましたが、条件分岐処理はなんとそれ以上です。
実際のソースコードは、こんな風に条件分岐だらけなんです。
今回は、条件分岐処理とはどのようなもので実際どう使われるのか?ということを実例や現場の豆知識を交えながら、分かりやすく説明していきたいと思います。
条件分岐処理とは何か?
プログラムを書いていると、「こういう場合はこの処理」「別の場合はこの処理」というように、条件によって処理を分けたいときがあります。
例えば、
①ログインしてたら→HOMEを出す
②ログインしてなかったら→ログイン画面に飛ばす
①在庫があるなら→残り在庫数を出す
②在庫が0なら→「売り切れ」という表示を出す
①男性の場合→男性向けおすすめ商品を表示する
②女性の場合→女性向けおすすめ商品を表示する
③不明の場合→ユニセックスおすすめ商品を表示する
このような場合です。
こういったときに使うのが「条件分岐処理」です。
if文とswitch文の使い分け方
条件分岐には「if(イフ)文」と「switch(スイッチ)文」の2種類があります。
if文
if文は、上から順番に条件を判定していき、条件が合致したら「指定の処理」を実行します。
どれかの条件に合致するとそれ以降の条件判定は行いません。
if文の特徴は、色々な条件パターンを書くことが出来る点です。
switch文
switch文は、ある特定のデータの値のパターンをチェックします。
特定のデータ(下の例では変数A)に対して、多くの比較値で条件分岐する場合は、if文よりもswitch文の方が簡潔に書くことが出来ます。
switch文は、ある特定のデータの値をチェックしたい場合に便利です。
【現場のコツ】
if文はどんな条件分岐でも書くことが出来ますが、switch文で書いた方がソースコードの処理や可読性が簡潔になる場合はswitch文を使うといったように、用途で使い分けましょう!
実際のWebサービスでの使用例
if文の実例
実際のWebサービスでは、例えば「入力チェック」を行うような場合などに使います。
ログイン画面の「メールアドレス入力欄」にユーザーが入力したアドレスが
・未入力でないか
・正しい形式で入力されているか
・文字数が長すぎないか
このようなチェックを行うような場合です。
実際のソースコードはこんな感じになっています。
// メールアドレスの入力チェック if (empty($user_email)) { $err['user_email'] = 'メールアドレスを入力して下さい。'; } elseif (!filter_var($user_email, FILTER_VALIDATE_EMAIL)) { $err['user_email'] = 'メールアドレスが不正です。'; } elseif (strlen(mb_convert_encoding($user_email, 'SJIS', 'UTF-8')) > 200) { $err['user_email'] = 'メールアドレスは200字以内で入力して下さい。'; }
最初の条件は「if」、2個目以降は「elseif」という形で条件指定する決まりになっています。
ちなみに、上記のチェック処理では「empty」「filter_var」「strlen」といったPHPの標準関数を活用しています。メールアドレスのチェックは「@が付いているか」「ドットが適切な位置に付いているか」など様々なチェックを行わなければならないのですが、関数を使えばそういった面倒な処理は全て1発で行ってくれます。
関数について詳しくはこちらの記事をどうぞ。
switch文の実例
これは画面からファイルをアップロードした際の処理です。
switch ($_FILES[$attr_name]['error']) { case UPLOAD_ERR_OK: // 処理成功 // 成功時処理 break;
case UPLOAD_ERR_NO_FILE: // ファイル未選択 // エラー処理 throw new RuntimeException('ファイルが選択されていません。'); case UPLOAD_ERR_FORM_SIZE: // フォーム定義の最大サイズ超過 // エラー処理 throw new RuntimeException('ファイルサイズが大きすぎます。'); default: // どの条件にもマッチしない場合の処理 throw new RuntimeException('エラーが発生しました。');
}
この例では、$_FILES[$attr_name]['error']という変数の中身が
・UPLOAD_ERR_OKの場合
・UPLOAD_ERR_NO_FILEの場合
・UPLOAD_ERR_FORM_SIZEの場合
・それ以外の場合
というチェックを行っています。
このように、1つのデータに対して複数の値をチェックしたい場合はswitch文が向いています。
もしこの処理をif文で書いたとしたら、以下のようになります。
if ($_FILES[$attr_name]['error'] == UPLOAD_ERR_OK) { // 成功時処理 break; } else if ($_FILES[$attr_name]['error'] == UPLOAD_ERR_NO_FILE) { // エラー処理 throw new RuntimeException('ファイルが選択されていません。'); } else if ($_FILES[$attr_name]['error'] == UPLOAD_ERR_FORM_SIZE) { // エラー処理 throw new RuntimeException('ファイルサイズが大きすぎます。'); } else { // どの条件にもマッチしない場合の処理 throw new RuntimeException('エラーが発生しました。'); }
これだと、条件式に毎回「$_FILES[$attr_name]['error'] ==」と書かなければならず面倒だし、ソースコードも見づらいですよね。
現場のノウハウ
プログラミングしていると条件分岐処理は必ず出てきますが、多く使い過ぎると後からソースコードを見たときに、自分でも何をやっているのか分からなくなります。
後から誰がソースコードを見ても分かりやすいように、条件分岐処理は出来るだけシンプルに書くように心がけましょう。
どうしても複雑な条件を書かなければならない場合は、ソースコードの条件式の部分に「意図や目的」をコメントとして細かく書いておきましょう。
また、実際の開発でif文を書く際、例えばログインチェック処理などで
if (ログインしていたら) { HOME画面へ遷移する } else if (ログインしていなかったら) { ログイン画面へ遷移する }
普通に考えるとこのような条件式になるのですが、人間というものは必ずミスを犯すもので「バグは常に発生する前提」で考えておく必要があります。
また、不正アクセスなどにより何か想定外のデータが入ってくる可能性もあるかもしれません。
そういったことが発生し、万が一条件式に漏れがあった場合、上記の形だと「どちらの条件にも当てはまらない」ことが発生してしまうかもしれません。
すると、処理が先に流れてしまい、思わぬ挙動が発生してしまうかもしれないので、こういった場合は以下のように「else」で想定外を吸収出来るように書いておきます。
if (ログインしていたら) { HOME画面へ遷移する } else { // それ以外なら ログイン画面へ遷移する }
このように書いておけば、もし条件式にバグや漏れがあっても「それ以外なら(else)」に必ず入るので、ログイン画面に遷移させることが出来ます。
【現場のコツ】
プログラマーの想定外の事が起こっても、おかしな挙動が起こらないようelseを活用しよう(想定外が発生しても問題無い方の処理をelseにしておきます)
こういったことを意識することで、バグの少ないプログラムが書けるようになっていきます。
まとめ
基本は「if文」を使う。
特定のデータの値パターンをチェックしたい場合は「switch文」を使う。
条件分岐が複雑になる時はソース内にコメントを書いて分かりやすくする。
バグが発生する前提でelseを使ってリスクを軽減する。
条件分岐処理を使いこなすことで、複雑な処理を実現することが出来るようになります。
上記のような点に気をつけて、上手に使いこなしていきましょう!
プログラミングのもう一つの重要な考え方「ループ処理」は以下の記事で解説しています。