2012-12-14 18 views
11

voglio fare:Come scrivere più istruzioni try in un blocco in python?

try: 
    do() 
except: 
    do2() 
except: 
    do3() 
except: 
    do4() 

Se do() fallisce, eseguire DO2(), se DO2() non riesce troppo, exceute DO3() e così via.

migliori saluti

+4

ho la sensazione che descrivono il tuo caso specifico utilizzo porterà ad una risposta con una soluzione più elegante ... – Triptych

risposta

9

mi piacerebbe scrivere una funzione wrapper rapido first() per questo.

utilizzo: value = first([f1, f2, f3, ..., fn], default='All failed')

#!/usr/bin/env 


def first(flist, default=None): 

    """ Try each function in `flist` until one does not throw an exception, and 
    return the return value of that function. If all functions throw exceptions, 
    return `default` 

    Args: 
     flist - list of functions to try 
     default - value to return if all functions fail 

    Returns: 
     return value of first function that does not throw exception, or 
     `default` if all throw exceptions. 

    TODO: Also accept a list of (f, (exceptions)) tuples, where f is the 
    function as above and (exceptions) is a tuple of exceptions that f should 
    expect. This allows you to still re-raise unexpected exceptions. 
    """ 

    for f in flist: 
     try: 
      return f() 
     except: 
      continue 
    else: 
     return default 

# Testing. 

def f(): 
    raise TypeError 

def g(): 
    raise IndexError 

def h(): 
    return 1 


# We skip two exception-throwing functions and return value of the last. 
assert first([f, g, h]) == 1 

assert first([f, g, f], default='monty') == 'monty' 
0

è necessario specificare il tipo di eccezione che si sta tentando di catturare ogni volta.

try: 
    do() 
except TypeError: #for example first one - TypeError 
    do_2() 
except KeyError: #for example second one - KeyError 
    do_3() 

e così via.

+0

Se io non conosco il tipo di eccezione? – alwbtc

+2

@alwbic: se non si conosce il tipo di eccezione, non si sa come gestire l'eccezione. – BrenBarn

+0

@alwbic Sono sicuro che devi sapere che tipo/i di eccezioni si aspettano. – alexvassel

21

Se davvero non si preoccupano le eccezioni, si potrebbe ciclo su casi fino ad avere successo:

for fn in (do, do2, do3, do4): 
    try: 
     fn() 
     break 
    except: 
     continue 

Questo almeno evita di dover far rientrare una volta per tutti i casi. Se le diverse funzioni richiedono argomenti diversi, è possibile utilizzare functools.partial per "innescare" prima del ciclo.

+1

'pass' dovrebbe essere' continue' forse? Funziona come scritto ma 'continue' è semanticamente più chiaro. – Triptych

+0

@Triptych Vero, ciò indica meglio l'intento del segnale. Risposta modificata –

4

Sembra una cosa veramente strana di voler fare, ma probabilmente ciclo le funzioni e scoppiare quando non c'erano eccezione sollevata:

for func in [do, do2, do3]: 
    try: 
     func() 
    except Exception: 
     pass 
    else: 
     break 
0

Ecco il modo più semplice che ho trovato, appena incorporare la prova sotto il precedente salvo.

try: 
    do() 
except: 
    try: 
     do2() 
    except: 
     do3() 
-1
import sys 

try: 
    f = open('myfile.txt') 
    s = f.readline() 
    i = int(s.strip()) 
except OSError as err: 
    print("OS error: {0}".format(err)) 
except ValueError: 
    print("Could not convert data to an integer.") 
except: 
    print("Unexpected error:", sys.exc_info()[0]) 
    raise 
+1

Questo non risponde affatto alla domanda! –

Problemi correlati