我应该在 PHP 代码中使用断言吗?

2022-08-30 07:58:19

一位同事在我们的库中添加了几次 assert 命令,在这些地方,我将使用 if 语句并引发异常。(在此之前,我甚至从未听说过断言。以下是他如何使用它的示例:

assert('isset($this->records); /* Records must be set before this is called. */');

我会做的:

if (!isset($this->records)) {
    throw new Exception('Records must be set before this is called');
}

通过阅读有关 assert 的 PHP 文档,看起来建议您确保 assert 处于活动状态,并在使用 assert 之前添加处理程序。我找不到他这样做的地方。

所以,我的问题是,鉴于上述情况,使用断言是否是一个好主意,我应该更频繁地使用它而不是if和异常?

另请注意,我们计划在各种项目和服务器上使用这些库,包括我们甚至可能不是其中一部分的项目(库是开源的)。这在使用断言时有什么区别吗?


答案 1

适用于大多数语言的经验法则(我模糊地知道)是,an用于断言条件总是正确的,而如果可以想象它有时会失败,则an是合适的。assertif

在这种情况下,我会说这是合适的(基于我对情况的弱理解),因为应该始终在调用给定方法之前设置。因此,未能设置记录将是程序中的错误,而不是运行时条件。在这里,有助于确保(通过充分的测试)没有可能导致在没有设置的情况下调用正在保护的代码的程序执行路径。assertrecordsassertassertrecords

与 相反,使用的好处是,通常可以在生产代码中关闭,从而减少开销。可以想象,在生产系统中,最好处理的情况可能发生在运行时,因此无法关闭它们不会丢失任何内容。assertifassertif


答案 2

将断言视为“权力评论”。而不是像这样的评论:

// Note to developers: the parameter "a" should always be a number!!!

用:

assert('is_numeric(a) /* The parameter "a" should always be a number. */');

含义完全相同,并且针对完全相同的受众,但第一个注释很容易被遗忘或忽略(无论有多少感叹号),而“power注释”不仅可供人类阅读和理解,而且在开发过程中也不断进行机器测试,如果您在代码和工作习惯中设置了良好的断言处理,则不会被忽略。

从这个角度来看,断言与if(错误)...和例外,它们可以共存。

是的,你应该注释你的代码,是的,你应该尽可能使用“电源注释”(断言)。


推荐