【问题标题】:Extended: what's the finally keyword for?扩展:finally 关键字的用途是什么?
【发布时间】:2013-09-20 20:24:44
【问题描述】:

好的,我理解为 this question 给出的“已接受的答案”,但我仍然不清楚应该在 finally 块中放入什么样的代码。

如果finally的使用是为了让未被捕获的异常抛出,并给系统一个通用的错误信息,不会为用户爆炸,如果捕获了一些异常,不会为用户显示两条错误信息吗?

[编辑]

就像@MarkBaker 所说,“finally”不是为了捕获未捕获的异常,通用的 catch(Exception $e) 就是这样做的。所以……它有什么用?或者换句话说,在没有finally的try/catch块之后,finally块做了什么我不能做的?

【问题讨论】:

  • finally 的使用不是to get the non-catched exceptions thrown and give a general error message,您使用通用的catch(Exception $e)...finally 用于无论是否捕获异常都是常见的代码(例如关闭文件句柄)
  • 我不知道是否有 PHP 特定的答案,或者是否可以使用 try/catch/finally 最佳实践。 stackoverflow.com/questions/1158667/…
  • @MikeB - 我认为当这个人说即使 try/catch 块退出或抛出另一个异常,finally将执行,这将是不同的,因为所有其余的代码都不会,但我在这里尝试过,如果我退出或在 try 或 catch 块内抛出另一个异常,finally 和其余代码(这些块之后的任何内容)具有相同的行为。
  • @MarkBaker - 我看不出一般的 catch(Exception $e) 如何获得未捕获的异常。我必须创建与抛出的异常类具有完全相同名称的 catch 块,并且如果我可以预见“抛出新异常”并且可以预见“抛出新 AnyException”,则不会导致任何未捕获的异常。
  • 您的 catch 块不必是“确切名称”:异常具有扩展层次结构,并且所有扩展都扩展 Exception 作为它们的曾祖父,然后 catch(Exception $e) 将捕获任何异常未被捕获中的其他显式异常类名显式捕获。如果我有 3 个不同的子异常都扩展了 PDO_Exception,那么 catch(PDO_Exception $e) 将捕获这三个中的任何一个

标签: php


【解决方案1】:

也许下面的解释会更好地帮助你理解它是如何工作的:

try {
    function1();//this might throw an exception
    function2();//if we want function2 to be executed regardless 
                //if an exception was thrown from function1() - this 
                //is not a good place to call it!
} catch (Exception $e) {
    echo $e->getMessage();
} finally {
    function2();//then the right place to write it will be in a finally clause.
}

function1() 抛出异常时 - function2() 将不会被执行 - 执行将“跳转”到 catch 部分。如果我们希望function2() 被执行而不管是否抛出错误,例如,如果function1() 打开一个到数据库的连接并运行一些选择并且function2() 关闭该连接,那么我们最好将调用function2()finally 块中,跟在catch 之后

【讨论】:

  • 即使不存在 finally 块并且在 try/catch 块之后,function2() 也会执行。唯一不会的方法是 function1() 不是由“Exception”类引发异常(未捕获的异常)。这就是重点:在这种情况下我想要执行什么样的代码。
  • @RafaelBarros 不一定:从catch 子句内部抛出另一个异常的情况如何? ;)
  • 如果我正确理解了场景,就会发生同样的行为,就像我在问题的 cmets 部分对@MikeB 所说的那样。 ps:我试过了。
  • @RafaelBarros 我不明白你的最后评论。此外,不建议更改问题,因为它会使所有已发布且有效的答案无效!最好提出一个新问题。
  • @RafaelBarros 如果在 catch 子句中执行的代码引发了另一个异常,那么你在 catch 之后编写的代码将不会被执行,除非它在 ​​finally 中。试试看!
【解决方案2】:

'finally' 块应该包含您想要执行的代码,而不管 try/catch 块的结果如何。例如,如果您尝试查询数据库并捕获错误,则无论数据库操作是否成功,您仍然可能希望关闭数据库连接。见下文:

open_database_conn();
try{
  query_database();
  return_result();
}
catch(Exception $e){
  echo $e->getMessage();
}
finally{
  close_database_conn();
}

【讨论】:

    猜你喜欢
    • 2011-12-10
    • 2016-10-28
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-10-26
    • 2014-05-26
    • 2011-01-21
    • 1970-01-01
    相关资源
    最近更新 更多