コード例

PHP用語集

カテゴリー: 制御構造  閲覧数:796 配信日:2010-05-22 10:16


投げない


例外を投げていない
・例外を「スロウ(投げる)」していないため、エラーが起こっても「トライ」が全部実行され「例外処理」も実行されない、無意味なサンプル
※「例外処理」は、「例外」が「スロウ(投げる)」されてはじめて実行される
 
   echo "--- 例外 テスト ---\n\n";//①
   
   try{
       echo "→→→ try 開始 →→→\n\n";//②
       #引数が不正な関数コール(「Warning」警告)
       //substr();
       echo "←←← try 終了 ←←←\n\n";
   }catch(Exception $e){
       echo "****** catch ******\n\n";
   }
   
   echo "--- 例外 テスト ---";

・結果
--- 例外 テスト ---

→→→ try 開始 →→→

←←← try 終了 ←←←

--- 例外 テスト ---


投げる


「例外」を「スロウ(投げる)」して「例外処理」を実行するサンプル
 
   echo "--- 例外 テスト ---\n\n";//①
   
   try{
       echo "→→→ try 開始 →→→\n\n";//②
       echo "- 例外が投げられました。-\n\n";
       throw new Exception("例外が投げられました。");//③「try」ブロックの処理はこの一文が実行された時点で中断。「Exception」クラスのインスタンスを生成し、コンストラクタに「"例外が投げられました。"」という文字列を渡している
       echo "←←← try 終了 ←←←\n\n";
   }catch(Exception $e){//④投げられた「例外」を「キャッチ」。「変数$e」は必ず「Exception」クラスのインスタンスが渡されることを想定した「catch」の引数。つまり、「throw文」によって投げられた「Exception」クラスのオブジェクトは「変数$e」に引数として代入され、キャッチブロック内で利用されることになる。
       echo "****** catch ******\n\n";
       echo '$e->getMessage() : ', $e->getMessage(), "\n\n";//キャッチブロック内の「例外処理」を実行
       //echo "\$e : \n", $e, "\n\n";
   }
   
   echo "--- 例外 テスト ---\n\n";//

・結果
--- 例外 テスト ---

→→→ try 開始 →→→

- 例外が投げられました。-

****** catch ******

$e->getMessage() : 例外が投げられました。

--- 例外 テスト ---


投げる順番


最初の「throw文」が実行される前に、コンストラクタ内の「throw文」が実行される例
    class NotException{}
   class Ex1 extends Exception{
       public function __construct($message = NULL, $code = 0){
           parent::__construct($message, $code);
           //throw new NotException; //「Not例外オブジェクト」を生成して投げようとしている//Fatal error:  Exceptions must be valid objects derived from the Exception base class
       }
   }
   
   try{
       throw new Ex1;//①「例外オブジェクト」を生成して投げようとしている
   }catch(Exception $e){
   }



0除算


エラーを発生させ、try~catchで例外を補足している例
・tryブロック内の処理でdivision関数の第2引数を0にして呼び出した際に例外が発生し、Exceptionクラスのオブジェクトが投げられる。続いて、「例外クラス名でExceptionを指定したcatchブロック」で例外が捕捉され、処理が行われていることが確認できる。なお、tryブロック内で例外が発生しなかった場合は、catchブロックの処理は行われない
function division($arg1, $arg2)
{
if ($arg2 === 0) {
throw new Exception('ゼロ除算はできません。<br>');
}
$answer = $arg1 / $arg2;
return $answer;
}

echo 'try catch start<br>', PHP_EOL;//定数 ソース上で改行

try {
echo 'try start<br>', PHP_EOL;
echo division(10, 2)."<br>", PHP_EOL;
echo division(10, 0), PHP_EOL;
echo 'try end<br>', PHP_EOL;
} catch (Exception $e) {
echo 'catch start<br>', PHP_EOL;
echo $e->getMessage(), PHP_EOL;
echo "例外コード:" . $e->getCode()."<br>", PHP_EOL;
echo "行番号:" . $e->getLine()."<br>", PHP_EOL;
echo "<pre>バックトレース:<br>";
p( $e->getTrace( ) );
echo "</pre>";
echo 'catch end<br>', PHP_EOL;
}

echo 'try catch end<br>例外処理後、スクリプト継続', PHP_EOL;
/* 出力:
try catch start
try start
5
catch start
ゼロ除算はできません。
例外コード:0
行番号:19

バックトレース:

Array
(
[0] => Array
(
[file] => /○○/PHPStyleNote/basic/exception/7.php
[line] => 30
[function] => division
[args] => Array
(
[0] => 10
[1] => 0
)

)

)

catch end
try catch end
例外処理後、スクリプト継続
*/


簡易クラス
class Calc
{
   public static function division($int1, $int2){
       try {
           if ($int2 == 0) {
               throw new Exception('0で割ろうとしました');
           }
           $answer = $int1 / $int2;
           echo $answer . "
";
           echo '割り算が終了しました' . "
";
       } catch (Exception $e) {
           echo $e->getMessage() . "
";
           echo '割り算が異常終了しました' . "
";
       }
   }
}

Calc::division(10, 2);
Calc::division(10, 0);

・結果
5
割り算が終了しました
0で割ろうとしました
割り算が異常終了しました

場合分け項目を増加
    function division($num1, $num2){//②
       try{
           if($num2 === 0)//「比較演算子===」等しい(型も同じ) ⑩
               throw new Exception('「0」で割ることは出来ません。');
           else if(!is_numeric($num1) || !is_numeric($num2))//「論理和||」いずれかのオペランドが「真」なら「true」 を返す
               throw new Exception('値が不正です。');//⑥
           return $num1 / $num2;//③ ⑧0÷10=0 「0を割る」は成立する。
       }catch(Exception $e){
           return $e->getMessage();
       }
   }
   
   echo division(10, 2), "\n";//①④
   echo division(10, ""), "\n";//⑤
   echo division(0, 10), "\n";//⑦
   echo division(10, 0), "\n";//⑨

・結果
5
値が不正です。
0
「0」で割ることは出来ません。

例外ごとのクラス作成
    class DivisionEx extends Exception{}//Exception」クラスを継承した「DivisionException」クラスを定義。“割算における「例外」”
   class DivisionIsZeroEx extends DivisionEx{//「DivisionEx」クラスを継承した「DivisionIsZeroEx」クラスを定義。“分母が「0」であるという「例外」”
       protected $message = '「0」で割ることは出来ません。';
   }
   class DivisionWrongValueEx extends DivisionEx{//「DivisionEx」クラスを継承した「DivisionWrongValueEx」クラスを定義。“値が不正であるという「例外」”
       protected $message = '値が不正です。';//⑮
   }
   
   class Division{//割算を行うためのクラス。コンストラクタに渡された2つの値をチェックし、問題があれば「例外」を投げ、問題がなければ(「例外」が投げられていなければ)演算結果をプロパティに保存
       private $result;//⑤⑳
       public function __construct($num1, $num2){
           if($num2 === 0)
               throw new DivisionIsZeroEx;
           else if(!is_numeric($num1) || !is_numeric($num2))
               throw new DivisionWrongValueEx;//⑬
           $this->result = $num1 / $num2;//④⑲
       }
       public function getResult(){//⑦
           return $this->result;
       }
   }
   
   function division($num1, $num2){//②⑪⑰
       try{//投げる元はココ
           $division = new Division($num1, $num2);//③⑫⑱
           return $division->getResult();//⑥⑧
       }catch(DivisionEx $e){//ここでキャッチ
           return $e->getMessage();//⑭
       }
   }
   
   echo division(10, 2), "\n";//①⑨
   echo division(10, ""), "\n";//⑩
   echo division(0, 10), "\n";//⑯
   echo division(10, 0), "\n";

・結果
5
値が不正です。
0
「0」で割ることは出来ません。


ファイルオープン


処理基点となるスクリプトをtry~catchすることで、全ての例外をそこで捕まえる例
class File
{
   public static function read($path)
   {
       if (false == file_exists($path)) {
           throw new Exception('ファイルが存在しません');
       }
       $fp = @fopen($path, 'r');
       if (false === $fp) {
           throw new Exception('ファイルのオープンに失敗しました');
       }
       $data = @stream_get_contents($fp);
       if (false === $fp) {
           throw new Exception('ファイルの読込に失敗しました');
       }
       return $data;
   }
}

class StringViewer
{
   public function display($path)
   {
       try {
           $data = File::read($path);
           echo $data;
       } catch (Exception $e) {
           die($e->getMessage());
       }
   }
}

$viewer = new StringViewer();
$viewer->display('C:/aaa.txt');

・結果
ファイルが存在しません


週間人気ページランキング / 11-16 → 11-22
順位 ページタイトル抜粋 アクセス数
1 ブラウザを閉じたらセッションデータはどうなるの? | セッション 8
2 Parse error: syntax error, unexpected 'public' (T_PUBLIC) | Parse error(エラーメッセージ) 5
3 Fatal error: Access level to ▲::$△ must be protected (as in class ●) or weaker | Fatal error(エラーメッセージ) 4
3 Warning: strlen() expects parameter 1 to be string, array given in ○○.php on line △△ | Warning(エラーメッセージ) 4
4 PHPで定数を定義する方法は2種類ある / 配列定数の定義 3
4 インポートするデータを受信できませんでした。ファイル名が送信されていないか、ファイルサイズが PHP の設定で許可された最大値を超えています。FAQ 1.16 をご覧ください | エラーメッセージ 3
4 ブラウザを閉じたらセッションデータはどうなるの? | セッション 3
4 クラスの継承 | クラスとオブジェクト 3
5 curl で Cookie を使用する 2
5 例外処理 | 制御構造 2
5 Fatal error: Uncaught Error: Call to a member function modify() on string | Fatal error(エラーメッセージ) 2
5 関数定義内での「外部ファイル読込」 | 制御構造 2
5 set_error_handler | 例外処理(制御構造) 2
5 ( ! ) Fatal error: Uncaught PDOException: SQLSTATE[HY093]: Invalid parameter number: parameter was not defined | Fatal error(エラーメッセージ) 2
5 コード例 … 「例外処理」はネストすることができる 2
5 PHP用語 2
5 register_shutdown_function | 関数処理 関数 2
6 クロージャ | 関数 1
6 session.cookie_lifetime / session.use_cookies | セッション 1
6 セッション管理が必要な理由は、HTTPプロトコルには状態を保持する機能がないため | セッション 1
2024/11/23 1:01 更新
指定期間人気ページランキング / 2020-5-28 → 2024-11-22
順位 ページタイトル抜粋 アクセス数
1 PHP用語 6664
2 ブラウザを閉じたらセッションデータはどうなるの? | セッション 2387
3 Parse error: syntax error, unexpected 'public' (T_PUBLIC) | Parse error(エラーメッセージ) 2300
4 ブラウザを閉じたらセッションデータはどうなるの? | セッション 1599
5 【テスト投稿】テスト | 1132
6 セッション管理が必要な理由は、HTTPプロトコルには状態を保持する機能がないため | セッション 978
7 PHPで定数を定義する方法は2種類ある / 配列定数の定義 849
8 Fatal error: Access level to ▲::$△ must be protected (as in class ●) or weaker | Fatal error(エラーメッセージ) 811
9 Fatal error: Uncaught Error: Call to a member function modify() on string | Fatal error(エラーメッセージ) 786
10 コード例 … 「例外処理」はネストすることができる 770
10 Fatal error: require_once(): Failed opening required 'PEAR.php' | Fatal error(エラーメッセージ) 770
11 curl で Cookie を使用する 739
12 定数 708
13 Fatal error: Uncaught RuntimeException: SplFileObject::__construct(): failed to open stream: Permission denied in | Fatal error(エラーメッセージ) 692
13 インターフェイス | クラスとオブジェクト 692
14 Fatal error: Uncaught HeadlessChromium\Exception\OperationTimedOut: Operation timed out (3sec) in | Fatal error(エラーメッセージ) 644
15 メンバー | クラスとオブジェクト 643
16 Warning: include() [function.include]: Failed opening '**.php' for inclusion (in | Warning(エラーメッセージ) 620
17 ( ! ) Fatal error: Uncaught PDOException: SQLSTATE[22001]: String data, right truncated: 1406 Data too long for column | Fatal error(エラーメッセージ) 588
18 Composer | 依存関係マネージャ 560
2024/11/23 1:01 更新