仓酷云

 找回密码
 立即注册
搜索
热搜: 活动 交友 discuz
查看: 1026|回复: 19
打印 上一主题 下一主题

[学习教程] PHP网页编程之PHP 5.0异常处置机制深度探究

[复制链接]
金色的骷髅 该用户已被删除
跳转到指定楼层
楼主
发表于 2015-2-4 00:22:01 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式

马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。

您需要 登录 才可以下载或查看,没有帐号?立即注册

x
你的留言本应该加入注册以及分页功能了,而如果你更强的话,UI(用户界面)也可以加强,完成之后,感觉是不是特有成就感?不管怎么样,咱好歹是写了一个动态网站程序了,放在自己的网站上耍耍吧。异常处置      本文面向但愿懂得PHP5异常处置机制的法式员。浏览本文你需求具有必定面向对象编程和PHP基本。

  PHP5内建的异常类需求有以下成员办法:

__construct()机关函数,需求一个失足信息和一个可选的整型毛病标志作参数getMessage()获得失足信息 getCode()
失足的代码 getFile()异常产生的文件getLine()异常产生的行数 getTrace()跟踪异常每步传递的线路,存入数组,前往该数组 getTraceAsString()和getTrace()功效一样,但可以将数组中的元素转成字符串并按必定格局输入
  可以看出来,Exception 类的布局和Pear_Error 很类似。当你的剧本中碰到一个毛病,你可以创立你的异常对象:

$ex = new Exception( "Could not open $this->file" );
  Exception类的机关函数将承受一个失足信息和一个毛病代码。

  利用 throw关头字

  创立一个Exception对象后你可以将对象前往,但不该该如许利用,更好的办法是用throw关头字来取代。throw用来抛出异常:

throw new Exception( "my message", 44 );
  throw 将剧本的履行中断,并使相干的Exception对象对客户代码可用。

  以下是改善过的getCommandObject() 办法:

  index_php5.php

<?php // PHP 5
require_once('cmd_php5/Command.php');
class CommandManager {
 private $cmdDir = "cmd_php5";

 function getCommandObject($cmd) {
  $path = "{$this->cmdDir}/{$cmd}.php";
  if (!file_exists($path)) {
   throw new Exception("Cannot find $path");
  }
 require_once $path;
 if (!class_exists($cmd)) {
  throw new Exception("class $cmd does not exist");
 }

 $class = new ReflectionClass($cmd);
 if (!$class->isSubclassOf(new ReflectionClass('Command'))) {
  throw new Exception("$cmd is not a Command");
 }
 return new $cmd();
}
}
?>
  代码中咱们利用了PHP5的反射(Reflection)API来判别所给的类是不是是属于Command 类型。在毛病的途径下履行本剧本将会报出如许的毛病:

Fatal error: Uncaught exception 'Exception' with message 'Cannot find command/xrealcommand.php' in /home/xyz/BasicException.php:10
Stack trace:
#0 /home/xyz/BasicException.php(26):
CommandManager->getCommandObject('xrealcommand')
#1 {main}
thrown in /home/xyz/BasicException.php on line 10
  默许地,抛出异常招致一个fatal error。这意味着利用异常的类内建有平安机制。而仅仅利用一个毛病标志,不克不及具有如许的功效。处置毛病标志掉败只会你的剧本利用毛病的值来持续履行。

  Try-catch 语句

  为了进一步处置异常,咱们需求利用try-catch语句―包含Try语句和最少一个的catch语句。任何挪用 能够抛出异常的办法的代码都应当利用try语句。Catch语句用来处置能够抛出的异常。以下显示了咱们处置getCommandObject()抛出的异常的办法:

  index_php5.php 后半段

<?php
// PHP 5
try {
 $mgr = new CommandManager();
 $cmd = $mgr->getCommandObject('realcommand');
 $cmd->execute();
} catch (Exception $e) {
 print $e->getMessage();
 exit();
}
?>
  可以看到,经由过程联合利用throw关头字和try-catch语句,咱们可以免毛病标志“净化”类办法前往的值。由于“异常”自己就是一种与其它任何对象分歧的PHP内建的类型,不会发生搅浑。

  假如抛出了一个异常,try语句中的剧本将会中断履行,然后即刻转向履行catch语句中的剧本。

  假如异常抛出了却没有被捕获到,就会发生一个fatal error。
处置多个毛病

  在今朝为止异常处置看起来和咱们传统的作法―查验前往的毛病标识或对象的值没有甚么太大区分。让咱们将CommandManager处置地更慎重,并在机关函数中反省command目次是不是存在。

  index_php5_2.php


<?php
// PHP 5
require_once('cmd_php5/Command.php');
class CommandManager {
 private $cmdDir = "cmd_php5";

 function __construct() {
  if (!is_dir($this->cmdDir)) {
   throw new Exception("directory error: $this->cmdDir");
  }
 }

 function getCommandObject($cmd) {
  $path = "{$this->cmdDir}/{$cmd}.php";
  if (!file_exists($path)) {
   throw new Exception("Cannot find $path");
  }
  require_once $path;
  if (!class_exists($cmd)) {
   throw new Exception("class $cmd does not exist");
  }

  $class = new ReflectionClass($cmd);
  if (!$class->isSubclassOf(new ReflectionClass('Command'))) {
   throw new Exception("$cmd is not a Command");
  }
  return new $cmd();
 }
}
?>

  这里有两个中央的挪用能够招致法式失足(__construct()和getCommandObject())。虽然如斯,咱们不需求调剂咱们的客户代码。你可以在try语句中增加浩瀚内容,然后在catch中一致处置。假如CommandManager 对象的机关函数抛出一个异常,则try语句中的履行中断,然后catch语句被挪用捕获相干的异常。一样地,getCommandObject()也是如斯。如许,咱们有同时存在两个潜伏的激发毛病的中央,和一个独一的语句来处置一切的毛病。这让咱们的代码看起来加倍整洁,又可以知足毛病处置的请求。和后面提到的PHP的传统的毛病办法比拟,明显很有优势。

  index_php5_2.php 后半段

  注重:虽然和index_php5.php比拟,前半段代码有两个能够失足的中央,这段代码和index_php5.php的后半段完整不异。


<?php
// PHP 5
try {
 $mgr = new CommandManager(); // potential error
 $cmd = $mgr->getCommandObject('realcommand');
 // another potential error
 $cmd->execute();
} catch (Exception $e) {
 // handle either error here
 print $e->getMessage();
 exit();
}
?>

  还有一个中央咱们没有提到。咱们如何辨别分歧类型的毛病?例如,咱们能够但愿用一种办法来处置找不到目次的毛病,而用另外一种办法来处置不法的command类。

  Exception类可以承受一个可选的整型的毛病标识,这是在catch语句中辨别分歧毛病类型的一个办法。

  index_php5_3.php


<?php
// PHP 5
require_once('cmd_php5/Command.php');
class CommandManager {
 private $cmdDir = "cmd_php5";
 const CMDMAN_GENERAL_ERROR = 1;
 const CMDMAN_ILLEGALCLASS_ERROR = 2;

 function __construct() {
  if (!is_dir($this->cmdDir)) {
   throw new Exception("directory error: $this->cmdDir", self::CMDMAN_GENERAL_ERROR);
  }
 }

 function getCommandObject($cmd) {
  $path = "{$this->cmdDir}/{$cmd}.php";
  if (!file_exists($path)) {
   throw new Exception("Cannot find $path", self::CMDMAN_ILLEGALCLASS_ERROR);
  }
  require_once $path;
  if (!class_exists($cmd)) {
   throw new Exception("class $cmd does not exist", self::CMDMAN_ILLEGALCLASS_ERROR);
  }

  $class = new ReflectionClass($cmd);
  if (!$class->isSubclassOf(new ReflectionClass('Command'))) {
   throw new Exception("$cmd is not a Command", self::CMDMAN_ILLEGALCLASS_ERROR);
  }
  return $class->newInstance();
 }
}
?>

  经由过程传递 CMDMAN_ILLEGALCLASS_ERROR和 CMDMAN_GENERAL_ERROR个中之一的参数给咱们抛出的异常对象,咱们就能够让客户代码辨别分歧类型的毛病,并界说分歧的处置战略。

  index_php5_3.php


<?php // PHP 5
try {
 $mgr = new CommandManager();
 $cmd = $mgr->getCommandObject('realcommand');
 $cmd->execute();
} catch (Exception $e) {
 if ($e->getCode() == CommandManager::CMDMAN_GENERAL_ERROR) {
  // no way of recovering
  die($e->getMessage());
 } else if ($e->getCode() == CommandManager::CMDMAN_ILLEGALCLASS_ERROR) {
  error_log($e->getMessage());
  print "attempting recovery\n";
  // perhaps attempt to invoke a default command?
 }
}
?>

  咱们也能够用另外一种办法来完成如许的后果―从最基本的Exception类中派生出代表分歧类型异常的子类,再抛出和捕获。


[1] [2] 下一页  

  只要实现最基本的功能就可以了 就是可以添加留言 然后可以显示留言,然后加入管理功能
沙发
发表于 2015-2-4 12:39:36 | 只看该作者
微软最近出的新字体“微软雅黑”,虽然是挺漂亮的,不过firefox  支持的不是很好,所以能少用还是少用的好。
谁可相欹 该用户已被删除
板凳
发表于 2015-2-4 20:17:47 | 只看该作者
建数据库表的时候,int型要输入长度的,其实是个摆设的输入几位都没影响的,只要大于4就行,囧。
小妖女 该用户已被删除
地板
发表于 2015-2-28 22:40:21 | 只看该作者
再就是混迹于论坛啦,咱们的phpchina的论坛就很强大,提出的问题一般都是有达人去解答的,以前的帖子也要多看看也能学到不少前辈们的经验。别的不错的论坛例如php100,javaeye也是很不错的。
因胸联盟 该用户已被删除
5#
发表于 2015-3-6 19:22:43 | 只看该作者
Apache不是非得用80或者8080端口的,我刚开始安得时候就是80端口老占用,就用了个 81端口,结果照常,就是输localhost的时候,应该输入为 localhost:81
再现理想 该用户已被删除
6#
发表于 2015-3-11 05:24:50 | 只看该作者
实践是检验自己会不会的真理。
飘灵儿 该用户已被删除
7#
发表于 2015-3-17 09:28:37 | 只看该作者
为了以后维护的方便最好是代码上都加上注释,“予人方便,自己方便”。此外开发文档什么的最好都弄齐全。我觉得这是程序员必备的素质。虽然会消耗点很多的时间。但是确实是非常有必要的。
只想知道 该用户已被删除
8#
发表于 2015-3-19 11:31:25 | 只看该作者
如果你可以写完像留言板这样的程序,那么你可以去一些别人的代码了,
若相依 该用户已被删除
9#
发表于 2015-3-27 08:41:51 | 只看该作者
兴趣是最好的老师,百度是最好的词典。
莫相离 该用户已被删除
10#
发表于 2015-3-31 16:55:18 | 只看该作者
首先我是坚决反对新手上来就用框架的,因为对底层的东西一点都不了解,造成知识上的真空,会对以后的发展不利。我的观点上手了解下框架就好,代码还是手写。当然啦如果是位别的编程语言的高手的话,这个就另当别论啦。
冷月葬花魂 该用户已被删除
11#
发表于 2015-4-12 13:27:54 | 只看该作者
开发工具也会慢慢的更专业,每个公司的可能不一样,但是zend studio是个大伙都会用的。
乐观 该用户已被删除
12#
发表于 2015-4-16 05:39:43 | 只看该作者
小鸟是第一次发帖(我习惯潜水的(*^__^*) 嘻嘻……),有错误之处还请大家批评指正,另外,前些日子听人说有高手能用php写驱动程序,真是学无止境,人外有人,天外有天。
老尸 该用户已被删除
13#
发表于 2015-4-16 23:39:52 | 只看该作者
至于模板嘛,各位高人一直以来就是争论不休,我一只小菜鸟就不加入战团啦,咱们新手还是多学点东西的好。
愤怒的大鸟 该用户已被删除
14#
发表于 2015-4-21 05:10:01 | 只看该作者
实践是检验自己会不会的真理。
山那边是海 该用户已被删除
15#
发表于 2015-4-27 23:13:13 | 只看该作者
对于初学者来说不推荐去拿钱买的。当然如果一个网站你经常去用,而且里面的资料也比较有用,最好还是买个会员比较好,毕竟那些也是别人的工作成果。
若天明 该用户已被删除
16#
发表于 2015-5-4 05:12:48 | 只看该作者
首先我是坚决反对新手上来就用框架的,因为对底层的东西一点都不了解,造成知识上的真空,会对以后的发展不利。我的观点上手了解下框架就好,代码还是手写。当然啦如果是位别的编程语言的高手的话,这个就另当别论啦。
柔情似水 该用户已被删除
17#
发表于 2015-5-8 00:58:57 | 只看该作者
Ps:以上纯属原创,如有雷同,纯属巧合
小女巫 该用户已被删除
18#
发表于 2015-5-8 20:47:45 | 只看该作者
有时候汉字的空格也能导致页面出错,所以在写代码的时候,要输入空格最好用引文模式。
变相怪杰 该用户已被删除
19#
发表于 2015-6-12 05:21:22 | 只看该作者
当留言板完成的时候,下步可以把做1个单人的blog程序,做为目标,
透明 该用户已被删除
20#
发表于 2015-6-17 04:54:29 | 只看该作者
环境搭建好,当你看见你的浏览器输出“it works\\\\\\\"时你一定是喜悦的。在你解决问题的时候,我强烈建议多读php手册。
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|Archiver|手机版|仓酷云 鄂ICP备14007578号-2

GMT+8, 2024-12-23 23:08

Powered by Discuz! X3.2

© 2001-2013 Comsenz Inc.

快速回复 返回顶部 返回列表