无需"finally"编程



我没有所需的支持finally的PHP版本,所以我想知道这是否是:

try {
work();
} catch (Exception $e) {
cleanup();
throw $e;
}
cleanup();

与完全相同

try {
work();
} finally {
cleanup();
}

无论在try块中发生什么,或者在以下catch情况下,finally块的要点都是执行。因此,如果仔细想想,finally块中的代码要么在成功执行try块之后执行,要么在抛出任何异常之后执行。因此,如果你像在解决方案中那样写它,那么你确实准确地模仿了这种情况。如果没有异常,则执行try/catch结构之后的代码;如果有异常——任何异常——你也要执行它

我认为finally支持的唯一情况可能会将您从中拯救出来,而您的版本本质上无法做到这一点,那就是您实际上提前中止了外部执行堆栈。例如,如果这个代码在一个函数中,并且您从try块中返回,那么finally仍然会被执行,但在您的手动实现中,它当然不能执行。

所以,如果你确保你没有提前离开,那么是的,它也应该以同样的方式工作。

没有多少方法可以提前离开函数而不抛出异常;return是最明显的,用exitdie或类似物中止程序将是另一种。

最后,代码块总是执行——如果有exeption,如果没有。但如果您捕获一个exeption并在捕获块之后执行cleanup(),那么是的,这基本上是一样的。

来自PHP文档:

在PHP 5.5及更高版本中,还可以在catch块之后指定finally块。finally块中的代码将始终在try-and-catch块之后执行,无论是否引发异常,并且在恢复正常执行之前执行。

如果您查看示例,您会注意到即使捕获到异常,finally块也将始终执行。然而,当出现异常时,代码将不会恢复,因此finally块是确保即使出现异常也始终执行某些代码行的好方法。

如果您的catch块使用return函数或类似函数,finally块将很重要。否则,将清理放入finally块或try/catch之后没有区别

以下是文档注释中有问题的示例:

只是一个为什么最终块是usefull(5.5)的例子

<?php
//without catch
function example() {
try {
//do something that throws an exeption
}
finally {
//this code will be executed even when the exception is executed
}
}
function example2() {
try {
//open sql connection check user as example
if(condition) { 
return false;
}
}
finally {
//close the sql connection, this will be executed even if the return is called.
}
}
?>

一般来说,是的

大多数情况下,这两个例子的作用相当:

<?php
function work_success() {
echo 'working' . PHP_EOL;
}
function work_fail() {
echo 'working with fail' . PHP_EOL;
throw new Exception('exception');
}
function cleanup() {
echo 'cleanup' . PHP_EOL;
}

不带finally:的代码

try {
work();
} catch (Exception $e) {
cleanup();
throw $e;
}
cleanup();

finally:的代码

try {
work();
} finally {
cleanup();
}

finally和非finally版本的work = work_success时的结果:

working
cleanup

finally和非finally版本的work = work_fail时的结果:

working
cleanup
Exception: exception

然而,也有一些注意事项

正如@poke所说,将您的示例与控制流机制结合使用可能会得到有趣的结果。下面用简单的return语句举例说明:

function test()
{
try {
return 'success';
} catch (Exception $e) {
cleanup();
throw $e;
}
cleanup();
}
echo test();

这将只输出success。除非引发异常,否则cleanup()不会被激发。根据先前的例子,与上述例子等效的finally对应物如下所示:

function test()
{
try {
return 'success';
} finally {
cleanup();
}
}
echo test();

请注意,无论有任何异常,此都将执行cleanup(),因此输出将为:

cleanup
success

对于一些人来说,令人惊讶的是finally块中的代码是在return语句之前执行的。只要你意识到这一点,就不会有任何问题。

相关内容

  • 没有找到相关文章

最新更新