PHP断言及其用法PHP断言及其用法

PHP具有巧妙的本机调试工具:PHP 断言。在简单的时刻,断言是函数程序以isert(),它在不满足条件时触发错误。

<?php

$a = 1;
assert($a === 1, '$a is not 1');
assert($a === 2, '$a is not 1');

?>

与调试条件不同,ASSERT()语法必须以积极的方式读取。当条件,aka作为第一个参数时,满意,一切都很好,而且进程持续;当不满足条件时,触发错误:错误的消息是第二个参数。

如果您有寿命较长的PHP编程,那么代码乱扔了以下内容:

<?php

$a = 1;
if ($a !== 1) {
    die('$a is not 1');
}

?>

然后,有几个原因,您应该考虑迁移到断言。

断言是积极的

断言中的条件必须是积极的,而不是消极的。因此,必须读取测试作为‘This is what I want’ and not ‘this is what I don’t want’。在阅读上面的两个示例时,您可以易于理解。

它也需要一个非常不同的思维方式。事实上,从手工断言迁移到断言的主要缺陷之一是切换条件。

可以配置断言

硬编码条件的关键问题是他们持续到守则直到生产的倾向。检查生产中的价值是不好的,如果发生任何事情,请单独杀死整个脚本。因此,必须删除该代码,就像任何调试代码一样。

这是断言闪烁的地方:通过简单地将Assert_active设置设置为false,在执行期间忽略断言。

<?php

assert_options(ASSERT_ACTIVE, 0);
$a = 1;
// This is now totally hidden
assert($a === 2, '$a is not 1');

?>

零成本 assertions

实际上,他们也被称为‘zero-cost’断言。这意味着,当断言处于非活动状态时,即使不会执行参数。例如,以下脚本调用foo()更好地使错误消息更好,并同时记录它。

<?php

$a = 1;
// This is now totally hidden
assert($a === 2, foo('a').' is not 1');

function foo($name) {
    print __FUNCTION__.PHP_EOL;
    
    // Log info
    Log::LogWarning($name.' failed');
    
    // beautifying the message...
    return 'The variable named '.$name;
}

?>

在正常函数调用中,必须先调用foo(),并且必须每次调用它:PHP必须为错误消息构建值,然后将其传递给Assert()。因此,为错误消息收集的调试信息总是昂贵,将慢速应用程序。

禁用断言时,跳过两个参数,导致无绕路。现在被测试的测试完全忽略了,代码根本不会放缓。

这是一个重要的优势:可以通过简单的指令开关从所有代码中删除所有断言。没有代码审查,没有Grep,只是禁用,再也没有见过。

点菜:死亡或警告

当您认为断言可能产生致命错误或简单警告时,它更好。代码中的代码中的硬编码exit()可以简单地配置断言。

  • Assert_Warning:PHP发出警告,但继续执行
  • assert_bail:php在断言失败时结束脚本的执行。

这非常有用:某些条件可能是至关重要的,并且应该停止整个代码。其他人是简单的未引发的情况,应举报以后审查。

用断言测试什么

断言非常适合检查代码的部分。在一行中,您可以确保表达式符合一些标准。因此,验证传入数据或变量类型非常常见。

<?php

function foo($a, $b) {
    assert(is_int($a), '$a must be an integer';
    assert(is_int($b), '$b must be an integer';
    assert($b === 0, '$b can\'t be 0';
    
    return $a / $b;
}
?>

这在代码的早期阶段非常有效,实际上可以发送到foo()。一旦错误变为回收,可以在代码中添加断言以警告它。通常,代码然后接近发射点。此外,当对错误进行错误时,整个代码立即停止,而不是搞乱应用程序的其余部分。

总之,断言是可执行评论。

断言还在调试

查看该示例,断言实际上看起来像一个弱的解决方案来使代码强大。首先,PHP具有标量型 - 提示,并添加‘int’在函数中,签名将提供更好的测试。

此外,当$ B为0时,应该有一个比简单错误消息更强大的反馈:抛出分区ZeroError异常怎么样?事实上,这是一个运行时问题,不仅仅是一个发展问题。

最后,应该写这个简单的例子:

<?php

function foo(int $a, int $b) {
    if ($b === 0)  
        throw new DivisionByZeroError('$b can\'t be 0');
    }
    
    return $a / $b;
}

?>

避免对非受控资源的断言

一种通常看起来像断言的好处的一种情况是数据库连接。每个人都有读取代码(Ext / MySQL是预期的):

<?php

$mysql = mysql_connect('localhost', 'web', 'password') or die("No database connexion"); 

assert(is_resource($mysql), "No database connexion");

?>

这里的断言不是一个好主意:数据库连接可能会或可能不可用,并且无法将其放在控制下。因此,断言不会在这里提供帮助。

断言后怎么办?

所以,似乎是一个很好的临时工具。然而,我们已经达到了他们的主要限制:很好,可以通过简单的PHP指令呼叫来删除它们,但这并不是’以任何方式应对这种情况。在生产中,没有断言,代码将继续执行。由于错误的表达式,数据将被损坏。该错误没有神奇地删除。

如果在生产中满足错误,我建议使用异常(或trigger_error())替换断言。这样,日志记录和监控可以拿起问题并将其报告给编码器。那’s important.

万一你只想要一个金丝雀,它会向你发出关于代码的某个点的潜在问题,而不阻止它,然后断言很棒。

开发期间调试的断言

另一方面,断言在开发期间发现错误。例如,在为exakat开发新分析的同时,我们必须依靠令牌名称及其关系。目前,有114种不同的令牌和67种关系。那些令牌随着时间的推移而发展,他们的关系是:每当其中一个都被过时,我们增加了一个断言。

该断言在这里作为一个故障安全:它触发早期警告,通常靠近原产地。然后,我们可以提前修复这个名称,或者决定将其保持在以后,同时知道它。代码没有’T在几次运行后发出警告,是时候考虑删除断言了。

这是一个经典的开发错误:我们希望尽可能经常检测到这种情况,因此赢得了’甚至去生产。断言是最好的工具:积极开发,并在生产中删除。

断言是临时服务

最终,断言是一种开发工具,应该这样用:它们很容易写,而且比评论更好。随时他们可以尽早发现问题是一个很好的用法。随着代码的成熟和稳定性,它们倾向于升级到异常,甚至更好,刚刚消失。

2 thoughts on “PHP断言及其用法

  1. pingback: PHP每月注释–2018年2月| phpstorm博客

  2. pingback: 今月のPHP - 2018年2月| Jetbrainsブログ.

评论被关闭。