簡體   English   中英

Python中ZeroDivisionError的好處

[英]Benefits of ZeroDivisionError in Python

假設我有兩個變量x和y,它們可以是任何值。 我必須將x除以y。 y可以為零。 現在我有兩種方法

1)

if y == 0:      
    continue # or break, supposing there is a loop going on.

2)

try:
    print 1/0
except ZeroDivisionError as e:
    print e
finally:
    print "got"

我的問題是,方法2比方法1有什么好處嗎?如果是,那么這又是什么呢?

try / except可能稍微快一點

通常,“ Python方式”是嘗試做您想做的事情,並在錯誤不起作用時處理錯誤(“ 比權限更容易獲得寬恕 ”),而不是預先檢查(“ 先看后看 ”) 飛躍 ”),以在將來提供更大的靈活性。

看起來y通常是代碼中的整數( int實例)。但是,請想象您的需求在不斷發展,並且yNewClass的實例,現在可以容納-0.0001類的值。

為了保持與您的應用程序的兼容性,編寫了NewClass.__eq__() ,以便if y == 0進行整數比較( 在這種情況下為True ),但是NewClass.__truediv__使用浮點值,因此1 / y不會返回錯誤。

因此,如果您使用, if應用程序的行為類似於-0.0001 == 0而使用except ZeroDivisionError可以正確處理新行為。

class NewClass(int):
    def __eq__(self, other):
        return int(self) == int(other)
    def __truediv__(self, other):
        return self.value / other

y = NewClass(-0.0001)

if y != 0:
     print 1 / y  # not printed

try:
    print 1 / y  # printed
except ZeroDivisionError:
    pass

從性能的角度來看,我要說選項2是否比選項1有任何好處取決於y為0的頻率。

如果y為0是常見的,則選項2不太可取,因為它最終會非常頻繁地引發ZeroDivisionError,而執行if y == 0:if y != 0:檢查將減少耗時。

但是,如果y很少為0(這是例外情況),那么選項2將是更可取的,因為您將沒有執行if檢查的開銷,而且很少會引發錯誤。

時間示例-

In [4]: def func2(lst):
   ...:     for i in lst:
   ...:         try:
   ...:             x = 10/i
   ...:         except ZeroDivisionError:
   ...:             pass
   ...:

In [5]:

In [5]: def func1(lst):
   ...:     for i in lst:
   ...:         if i != 0:
   ...:             x = 10/i
   ...:

In [6]: lst1 = [0 for i in range(100)]

In [7]: import random

In [8]: lst2 = [random.randrange(0,5) for i in range(100)]

In [9]: lst3 = [random.randrange(0,15) for i in range(100)]

In [10]: lst2.count(0)
Out[10]: 24

In [11]: lst3.count(0)
Out[11]: 5

In [12]: %timeit func1(lst1)
100000 loops, best of 3: 3.56 µs per loop

In [13]: %timeit func2(lst1)
10000 loops, best of 3: 50.6 µs per loop

In [14]: %timeit func1(lst2)
100000 loops, best of 3: 7.73 µs per loop

In [15]: %timeit func2(lst2)
10000 loops, best of 3: 18 µs per loop

In [16]: %timeit func1(lst3)
100000 loops, best of 3: 8.76 µs per loop

In [17]: %timeit func2(lst3)
100000 loops, best of 3: 9.88 µs per loop

即使只有5%的數字為0, if循環仍然比try/except塊更具性能。

基本上,例外應該針對例外情況。

暫無
暫無

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

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