1

在 PHP 中,我们可以通过在函数开头使用 @ 来禁用特定函数的错误报告:

错误控制运算符

PHP 支持一种错误控制运算符:at 符号 (@)。当附加到 PHP 中的表达式时,该表达式可能生成的任何错误消息都将被忽略。

例如:

@mail(...)

如果有错误,则不会返回任何错误,这是一种不好的做法吗?为什么?

4

4 回答 4

5

是的,这是不好的做法。这主要是因为它允许懒惰的代码编写,当你应该暴露和纠正你得到的错误而不是仅仅抑制它们,然后有一天当你的代码不起作用并且你无法弄清楚为什么时会感到惊讶。

于 2013-07-30T00:33:41.220 回答
2

你构建程序的方式应该处理错误,而不是隐藏它们。如果函数可能会产生错误,那么您应该编写代码来处理它。这是一个例子。

假设我有一个名为 $myarray 的数组,我想遍历它:

foreach($myarray as $value) {
    print $value;
}

如果 $myarray 的存在是有条件的(即它可能是从从数据库中提取的数据创建的),那么 foreach() 循环将失败,因为 $myarray 不是变量。为了处理这种情况,我可能会像这样编写上面的循环:

if(isset($myarray) && is_array($myarray)) {
    foreach($myarray as $value) {
        print $value;
    }
}

这将在尝试执行循环之前验证数组是否确实存在。这样,foreach() 就不能因为这个原因抛出错误,我也不必压制任何错误。

在代码的设计中应避免潜在的错误。应该捕获不可避免的错误,以便向用户显示有用的非极客消息,以便他们知道如何响应错误。或者更好的是,如果程序可以规避错误并无论如何安静地完成任务,它应该这样做。

在 mail() 的情况下,如果它会抛出一个错误,它为什么会那样做呢?您是否应该为它创建一个意外事件,例如另一种发送电子邮件的方法,或将其排队以供以后发送,或其他选项?你不想抑制错误,你想处理它。

于 2013-07-30T00:37:16.420 回答
1

是的,这是一个不好的做法。例如,用户想在您的网站上注册,您将通过邮件向他发送激活链接或其他重要信息。您正在使用@mail,但由于内部错误(邮件服务器停机)或类似原因,无法发送邮件。用户会知道电子邮件没有发送吗?不,因为您使用 抑制了错误,@或者没有处理错误并通知用户。

于 2013-07-30T00:32:56.000 回答
0

使用 PHP 错误控制运算符@不好的原因有以下几点:

1-来自 PHP 手册

目前,“@”错误控制运算符前缀甚至会禁用将终止脚本执行的严重错误的错误报告。除此之外,这意味着如果您使用“@”来抑制某个函数的错误,并且该函数不可用或输入错误,则脚本将在那里死掉,而不会说明原因。

2-如果您使用@过以下功能,您可能仍会使用已弃用的功能:

if(eregi("a", "abc")) echo "a";

产生此错误:

 Deprecated: Function eregi() is deprecated in D:\htdocs\test.php on line 2

使用时if(@eregi("a", "abc")) echo "a";不发出任何消息。

3- 其他事实:

http://us3.php.net/manual/en/language.operators.errorcontrol.php#99805

请注意,使用 @ 非常慢,因为 PHP 会产生开销来以这种方式抑制错误。这是速度和便利性之间的权衡。

http://us3.php.net/manual/en/language.operators.errorcontrol.php#85042

  • 设置的错误处理程序被调用,无论错误报告设置在什么级别,或者语句前面是否有 @

  • 由错误处理程序来赋予不同错误级别的某些含义。即使错误报告设置为 NONE,您也可以让自定义错误处理程序回显所有错误。

  • 那么@运算符是做什么的呢?它暂时将该行的错误报告级别设置为 0。如果该行触发错误,错误处理程序仍将被调用,但会以错误级别 0 调用

http://us3.php.net/manual/en/language.operators.errorcontrol.php#94004

请注意在 include() 之前的语句中使用错误控制运算符,如下所示:

<?PHP (@include("file.php")) OR die("Could not find file.php!"); ?>

因此,包含文件的错误报告级别也设置为零。因此,如果包含的文件中有一些错误,它们将不会显示出来。

最后,可以集中管理所有应用程序的错误处理,而不仅仅是特定功能。

于 2013-07-30T01:39:33.983 回答