2013-05-26 62 views
2

通常可以使用try/except塊來運行一堆語句,直到其中一個語句導致異常。運行幾個命令,直到不會發生異常? (Python)

我想做相反的事 - 運行一組語句,其中每個語句都可能導致異常,但其中一個不會。

下面是一些僞代碼:

try: 
    c = 1/0  # this will cause an exception 
    c = 1/(1 - 1) # this will cause an exception 
    c = int("i am not an integer") 
        # this will cause an exception 
    c = 1   # this will not cause an exception 
    c = 2   # this statement should not be reached 
    c = None  # this would be a final fallback in case everything exceptioned 

print c   # with this code, c should print "1" 

我想用這樣的方式是數據分析。用戶可以提供一些數據,這些數據可以是幾種不同格式之一。如果數據與格式不匹配,試圖解析各種格式將產生異常。可能有幾十種不同的可能格式。這些陳述將按照優先順序列出。只要其中一個解析器成功,那就是我想要的變量結果。

包裝每嘗試裏面嘗試/ excepts會導致一些醜陋的意大利麪代碼。

c = None 

try: 
    c = 1/0 
except: 
    pass 

if (c == None): 
    try: 
     c = 1/(1 - 1) 
    except: 
     pass 

if (c == None): 
    try: 
     c = int("i am not an int") 
    except: 
     pass 

... and so on 

有沒有更好的方法來做到這一點?

+1

我沒有看到你的意大利麪代碼在哪裏,最多隻有兩個縮進級別。 –

+0

也許這是一個錯誤的術語,但無論哪種方式,所有這些如果/嘗試/除了塊更難以閱讀比如果你可以只有一個語句列表... – fdmillion

回答

1

簡單地把它作爲一個函數怎麼樣?我使用你的僞代碼,所以沒有更好的功能,只是更具可讀性;

def doIt(): 

    try: 
     return 1/0 
    except: 
     pass 

    try: 
     return 1/(1 - 1) 
    except: 
     pass 

    try: 
     return int("i am not an int") 
    except: 
     pass 

c = doIt() 
+0

這工作很好,因爲我希望的解決方案的一半。唯一的缺點是不得不復制try/except塊,但是這與下一個解決方案相結合是最好的方法!謝謝! – fdmillion

3

我會說,使用lambda函數中的數組:

L = [ lambda : 1/0, 
     lambda : 1/(1 - 1), 
     lambda : int("i am not an int"), 
     lambda : 2 ] 

for l in L: 
    try: 
    x = l() 
    break 
    except: 
    pass 
print x 

在當前的例子/請你不必/使用輸入數據到你的測試,但最終你會以後對於lambda來說,這非常容易。

+0

@JoachimIsaksson爲什麼同行不接受編輯,而是自己編寫的與以前建議的完全一樣? –

+0

啊,是的,我可以看到,我休息時間滑倒了我的複製粘貼,認爲Joachim已經爲我修復了這個問題 – mogul

+0

@SaulloCastro對不起,從來沒有看到過你建議的編輯,我不是拒絕它的人。我剛剛添加了這個突破,因爲這是一個半工半讀的解決方案。 –