簡體   English   中英

最佳實踐:應該在Python代碼中大量使用異常處理程序,還是應該避免使用異常處理程序?

[英]Best practice: should I use exception handlers a lot in Python code, or should I avoid if it's possible?

我有一個項目,我必須經常這樣做:

if "something" in dict:
    some_var = dict["something"]
    del dict["something"]
else:
    error_handler_or_other_stuff()

但是我有使用這個的想法:

try:
    some_var = dict.pop("something")
except KeyError:
    error_handler_or_other_stuff()

我的問題是:一般來說,除了構造要處理異常之外,如何快速嘗試? 可以經常使用它嗎,還是“手動”執行該操作更快。 另外有時我不得不將值轉換為整數的情況:

try:
    some_var = int(dict.pop("something"))
except KeyError:
    error_handler_or_other_stuff("no such key")
except ValueError:
    error_handler_or_other_stuff("bad value for key")

現在帶異常的解決方案似乎非常不錯,因為我可以一步完成兩項檢查,所以我也從dict中刪除了原始鍵/值對,這就是問題的一部分。 因此,我至少可以說:這看起來像是一個優雅的解決方案。 但是,我不確定它是否速度更快,或者它是否還有其他缺點我應該擔心。

哪種構造使您的代碼更易於理解和維護? 選擇那個。

如果生成的代碼太慢,請返回並考慮其他錯誤處理策略是否更有效。

為什么不將dict.getdict.popdefault參數一起使用?

異常並不是特別慢。 顯然,異常處理要比簡單的if處理得多,但是除非您每秒進行一百萬次的處理,否則速度差異是可以忽略的。

您的示例是如此瑣碎,以至於沒有理由擔心速度的開始。 這樣的微優化花在思考它們上的時間比使用它們所節省的時間更多。

您提供的代碼絕對不錯,這就是例外的原因。

使用timeit模塊可以輕松回答以下這類性能問題:

setup = '''
d = {'a': 1}
k = 'b'
'''

LBYL = '''
if k in d:
    pass
else:
    pass
'''

EAPF = '''
try:
    d[k]
except KeyError:
    pass
'''

from timeit import Timer

print min(Timer(LBYL, setup).repeat(7, 1000000))
print min(Timer(EAPF, setup).repeat(7, 1000000))

結果顯示,if / else方法為0.0546,try / except方法為1.3370。 后者比前者慢25倍。

話雖如此,您通常應該使用最清晰的代碼。

旁注 :兩種方法對dict的子類給出不同的答案,這些子類定義了缺少值以返回值。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM