php找不到exception类,PHP中异常类Exception的应用

各类变成语言的异常处理大致类似,只是php不像java强制要求开发者捕获异常,而是淡化了异常处理来降低开发复杂度,可以看出一般的CMS框架很少使用try{}catch(){}结构编程,虽然并不会影响程序执行,但是会给某些粗心的程序埋下地雷,出了问题不好排查。所以,在PHP开发过程中还是尽量捕获异常和抛出异常,这样可以让我们的代码更健壮。

PHP处理异常的流程大致如下:在异常抛出时,其后面的代码不会继续执行,PHP会尝试查找匹配catch代码块,如果异常没有捕获,而且又没有set_exception_handler()作相应的处理的话,那么将发生一个严重的错误(致命错误),并且输出"Uncaught Exception"(未捕获异常)。例如:<?php

//我们先制造一个异常

function checkNum($number)

{

if($number>1)

{

throw new Exception("Value must be 1 or below");

}

return true;

}

function test()

{

//执行会抛出异常的代码

checkNum(2);

}

//测试函数

test();

//执行会抛出异常的代码

checkNum(2);

执行这段程序就会抛出异常,异常内容是在第7行,抛出了"Value must be 1 or below"的异常,而在调用checkNum()函数的第15行附近并未找到try{}catch(){}代码块,并且又没有set_exception_handler()作相应的处理,就会导致程序中断。

如果我们使用set_exception_handler来捕获,添加以下代码:function exception_handler ($exception)

{

echo "Hi, this is an Exception";

}

set_exception_handler('exception_handler');

之后,即使是程序的任意位置抛出异常均会跳转到exception_handler()函数进行处理。

其实,这样的功能和java的try{}catch(){}finally{}的处理倒是很像,不过又有很大的区别。java是之前不管你有没有捕获异常都会执行finally{}中的代码,而php发现了try{}catch(){}代码块处理了异常,并不会去调用set_exception_handler()定义的函数。例如:<?php

//我们先制造一个异常

function checkNum($number)

{

if($number>1)

{

throw new Exception("Value must be 1 or below");

}

return true;

}

function test()

{

try{

//执行会抛出异常的代码

checkNum(2);

}catch(Exception $e){

}

}

function exception_handler ($exception)

{

echo "Hi, this is an Exception";

}

set_exception_handler('exception_handler');

//测试函数

test();

运行之后,并不会有任何输出,说明exception_handler()并未执行。

话说,在test()函数中捕获了异常之后,如果当前并不需要处理异常咋办?test()可以继续抛出异常给上一层,即调用test()函数的第30行。

那么,修改代码如下:<?php

//我们先制造一个异常

function checkNum($number)

{

if($number>1)

{

throw new Exception("Value must be 1 or below");

}

return true;

}

function test()

{

try{

//执行会抛出异常的代码

checkNum(2);

}catch(Exception $e){

//将异常信息和异常代码抛出

throw new Exception($e->getMessage(), $e->getCode());

}

}

try{

//测试函数

test();

}catch(Exception $e){

echo "Hi, this is an Exception";

}

这样的处理在嵌套模块处理时非常有用,可以将各个地方的异常抛出到逻辑代码部分统一处理。

除了PHP自身的Exception之外,很多开源代码都会继承该类并实现自身的异常类。下面是官方手册给出的Exception的结构。<?php

class Exception

{

protected $message = 'Unknown exception';   // 异常信息

private   $string;                          // __toString cache

protected $code = 0;                        // 用户自定义异常代码

protected $file;                            // 发生异常的文件名

protected $line;                            // 发生异常的代码行号

private   $trace;                           // backtrace

private   $previous;                        // previous exception if nested exception

public function __construct($message = null, $code = 0, Exception $previous = null);

final private function __clone();           // Inhibits cloning of exceptions.

final public  function getMessage();        // 返回异常信息

final public  function getCode();           // 返回异常代码

final public  function getFile();           // 返回发生异常的文件名

final public  function getLine();           // 返回发生异常的代码行号

final public  function getTrace();          // backtrace() 数组

final public  function getPrevious();       // 之前的 exception

final public  function getTraceAsString();  // 已格成化成字符串的 getTrace() 信息

// Overrideable

public function __toString();               // 可输出的字符串

}

?>

实现自定义异常类<?php

header('Content-type:text/html;charset=utf-8');

/**

* 自定义一个异常处理类

*/

class MyException extends Exception

{

// 重定义构造器使 message 变为必须被指定的属性

public function __construct($message, $code = 0, Exception $previous = null) {

// 自定义的代码

// 确保所有变量都被正确赋值

parent::__construct($message, $code, $previous);

}

// 自定义字符串输出的样式

public function __toString() {

return __CLASS__ . ": [{$this->code}]: {$this->message}
";

}

public function customFunction() {

echo "A custom function for this type of exception
";

}

}

/**

* 创建一个用于测试异常处理机制的类

*/

class TestException

{

public $var;

const THROW_NONE    = 0;

const THROW_CUSTOM  = 1;

const THROW_DEFAULT = 2;

function __construct($avalue = self::THROW_NONE) {

switch ($avalue) {

case self::THROW_CUSTOM:

// 抛出自定义异常

throw new MyException('1 is an invalid parameter', 5);

break;

case self::THROW_DEFAULT:

// 抛出默认的异常

throw new Exception('2 is not allowed as a parameter', 6);

break;

default:

// 没有异常的情况下,创建一个对象

$this->var = $avalue;

break;

}

}

}

// 例子 1, 如果抛出的是一个自定义的异常,那么将会被MyException $e catch住

try {

$o = new TestException(TestException::THROW_CUSTOM);

} catch (MyException $e) {      // 捕获异常

echo "demo1:捕获到我的异常
", $e;

$e->customFunction();

} catch (Exception $e) {        // 被忽略

echo "demo1:捕获到普通异常
", $e;

}

// 例子 2, 如果抛出的是一个普通的异常,那么将会被Exception $e catch住

try {

$o = new TestException(TestException::THROW_DEFAULT);

} catch (MyException $e) {      //  不能匹配异常的种类,被忽略

echo "demo2:捕获到我的异常br/>", $e;

$e->customFunction();

} catch (Exception $e) {        // 捕获异常

echo "demo2:捕获到普通异常
", $e;

}

// 例子 3, 如果抛出的是一个自定义的异常,同时不存在MyException $e的catch, 那么将会被Exception $e catch住

try {

$o = new TestException(TestException::THROW_CUSTOM);

}catch (Exception $e) {        // 被忽略

echo "demo3:捕获到普通异常
", $e;

}

// 例子 4, 如果抛出的是一个普通异常,同时不存在Exception $e的catch, 此异常也不会被MyException $e catch住,只会抛出一个Fatal error:  Uncaught exception 'Exception'(未捕获的异常)

try {

$o = new TestException(TestException::THROW_DEFAULT);

} catch (MyException $e) {      // 捕获异常

echo "demo4:捕获到我的异常
", $e;

$e->customFunction();

}

// Continue execution

var_dump($o); // Null

echo "
";

使用异常处理虽然会增加编码的复杂度,但是对于程序的调试追踪非常有用,而且可以写出强壮的代码。

收藏随意^^请保留教程地址.

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值