【问题标题】:Why does removing this else make my code run so much faster?为什么删除这个 else 会使我的代码运行得这么快?
【发布时间】:2017-09-14 22:04:07
【问题描述】:

我正在使用 python 浏览一个数据库,并大量使用 tryexcept 来处理查询。在尝试优化我的代码时,我遇到了一个奇怪的问题。

这段代码:

try:
    cursor.execute("SELECT my_name FROM {}.{} LIMIT 1".format(myschema,mytable))
except(Exception, psycopg2.DatabaseError) as error:
    conn.rollback()
else:
    origName = cursor.fetchone()
    if origName is None:
        outputName = "ERROR2"
        return outputName
try:
    cursor.execute("SELECT different_column FROM {}.{} ORDER by a_column DESC LIMIT 1".format(myschema, mytable))
except(Exception, psycopg2.DatabaseError) as error:
    conn.rollback()
    try:...
        #more try/excepts and so on

运行整个数据仓库大约需要 19 分钟。

但是这个代码:

try:
    cursor.execute("SELECT my_column FROM {}.{} LIMIT 1".format(myschema,mytable))
except(Exception, psycopg2.DatabaseError) as error:
    conn.rollback()

origName = cursor.fetchone()
if origName is None:
    outputName = "ERROR2"
    return outputName
try:
    cursor.execute("SELECT different_column FROM {}.{} ORDER by a_column DESC LIMIT 1".format(myschema, mytable))
except(Exception, psycopg2.DatabaseError) as error:
    conn.rollback()
    try:...
        #exact same code with try/excepts and so on

字面意思是在大约 1-1.5 分钟内完成运行。如果我删除它,为什么它会快得多?是否有某些内容被跳过/忽略?我觉得我一定做错了。我真的不明白如何在try:except: 语句之后继续我的代码。

【问题讨论】:

  • 在第二个版本中,如果有错误,你 fetchone 无论如何,得到 None 并中止整个事情(或者可能fetchone 引发异常并且你以这种方式中止)。跨度>
  • 是的,在第一个中,如果没有错误,则运行 else 块。所以如果有错误,没有返回,第二次 try/except 运行。在第二个中,“else block”代码始终运行,因此如果您有错误,它将在第二个 try/except 运行之前以 outputname ERROR2 完成。也许尝试看看是否发生了这种情况。
  • 就是这样,谢谢@jh44tx

标签: python sql exception optimization try-catch


【解决方案1】:

这是因为在 python 世界中,try-except 块非常常见并且使用起来非常便宜。 try-except 比错误的 if 语句 if a != 1: 便宜。

else 子句本身很有趣。它在没有例外但在 finally 子句之前运行。这是它的主要目的。因此,如果您的 try-except 块没有捕获,则 else 语句仍会运行。这是它减慢代码速度的主要原因。

如果没有 else 子句,在最终确定之前运行附加代码的唯一选择是将代码添加到 try 子句的笨拙做法。这很笨拙,因为它有可能在不打算由 try 块保护的代码中引发异常。

在最终确定之前运行额外的未受保护代码的用例并不经常出现。因此,不要期望在已发布的代码中看到很多示例。比较少见。

Look at this post for some more information

【讨论】:

  • 这如何回答这个问题?您是说这 18 分钟的改进来自于对 else 语句本身的评估吗?我不确定,因为在第二个版本中,fetchone 块总是被执行,而在第一个版本中它不是,但第二个版本更快。也许你可以包括更多的细节,就像 jh44tx 在 cmets 中建议的那样,因为 else 语句中的块中的 return 语句,它会更快。
猜你喜欢
  • 2014-09-14
  • 2014-08-31
  • 2021-08-26
  • 2013-05-09
  • 2011-05-27
  • 2016-09-17
  • 1970-01-01
  • 2012-12-23
相关资源
最近更新 更多