python异常处理比PHP和/或其他语言更有效吗?

时间:2011-01-17 20:22:54

标签: php python exception programming-languages

我已经深入了解(至少在PHP中)使用try... catch块进行流量控制是badbadmojo。我学到的只是使用它们来处理意外错误,而不是确定程序的逻辑流程,因为catch块很昂贵。

现在我正在学习python,我看到了很多例外和EAFP原则。这是否意味着python在处理异常方面更有效率,所以我不需要为流量控制担心它们,或者原理是否仍然存在?如果没有,PHP是标准的异常(与其他语言相比),还是Python?

6 个答案:

答案 0 :(得分:13)

从历史上看,在C ++等语言中,与同一语言中的其他形式的流控制相比,异常非常缓慢。

在C ++中,有两件事在起作用:

  • 抛出异常非常复杂。堆栈需要解开,并且在本机代码中执行此操作比使用基于VM的高级语言更难
  • 定期,直接流量控制非常快。这是本机代码;分支是一对指令,其中回滚堆栈的异常调用复杂的算法(在大的,可能是压缩的表中查找堆栈数据,等等)。

这种性能上的差异导致了例外背后的一般智慧:只针对不寻常的事情,所以它只用于最有利的地方,而不是它会损害性能的地方。

这不适用于高级语言。这也有两个原因:

  • 回滚堆栈要简单得多。堆栈很容易检查;你不需要魔术表来知道在任何给定时间回滚堆栈的程度以及构造的对象。
  • 常规程序流本质上较慢。在基于VM的语言中,一切只需要更多的工作开始。

例外情况仍然不是免费的,但这种差异不再是令人担心的问题。这意味着在C ++中形成的一般智慧在这里被误用。在正常的程序流程中经常使用例外。

事实上,它们都是用语言构建的,在你一直使用的构造中。每次使用迭代器 - 每for x in xrange(1000)时,都会使用StopIteration异常来结束循环。

在Python中选择异常或线性流控制更有意义。不要根据表现选择,除非你实际上处于一个性能重要的内循环中;在这种情况下,一如既往,查看并确定它是否真正重要。

(我不能代表PHP。)

答案 1 :(得分:7)

我不相信EAFP鼓励使用流量控制的例外。相反,它告诉我们在引用之前我们不需要在对象的字典或属性中检查是否存在特定键。

将异常作为if语句的替代方案或使用正确的while语句,而不是在循环内使用breakcontinue,不属于该类别。这是懒惰的,容易出错的程序,应该避免。

答案 2 :(得分:3)

伟大的Alex Martelli在“Python In A Nutshell”一书中对EAFP与LBYL进行了很好的概述。 (他大力倾向于使用EAFP)

def值得阅读:
http://books.google.com/books?id=JnR9hQA3SncC&lpg=PA134&ots=JaaWGy-24u&dq=alex%20martelli%20eafp%20lbyl&pg=PA134#v=onepage&q&f=false

答案 3 :(得分:2)

回答这个问题:是的。 Python异常很便宜。如果测试仍然更便宜,那么是的,您应该只为“意外”情况使用异常,就像您希望代码在大多数情况下失败一样,在执行之前进行检查。由于if-check还将避免实际尝试以及异常的提升和捕获,因此在失败的情况下很多会更快。 (当然,除非测试本身很昂贵)。

但避免例外是没有意义的。 Python不会拖拽爬行,因为你捕获了很多例外。

和往常一样:没有分析的优化还为时过早。

答案 4 :(得分:0)

有一个特殊的异常只能在正常的执行流程中使用:StopIteration。这对我来说意味着Python的创建者并不认为异常开销是不合适的。

这是因为异常处理是超级高效还是其他语言比较慢是另一个问题......

答案 5 :(得分:0)

我已经做了一些阅读,并且已经意识到还没有人提到的另一个重要的事情:在Python中,错误和异常之间没有区别。我知道这一点,但直到现在我才认为我已经掌握了重要性。

在PHP中,你可以在$page->GetContent();块中包含try...catch所有你想要的内容,但是如果$page不是一个对象,那么你的应用程序仍会因为致命的问题而戛然而止错误。因此,在PHP(以及任何其他无法捕获错误的语言)中,您需要一定级别的LBYL。

Python基本上说,“这是愚蠢的,我应该能够抓住那些。”只是尝试做你需要做的事情,并处理except块中的任何后果。

这是我遇到的great article on exception handling