Imparare Python da zero #04: eccezioni e controllo di flusso con il costrutto try-except-else-finally

Python mette a disposizione un meccanismo per la gestione delle eccezioni costituito dal costrutto try/except. Riprendiamo l’esempio della divisione tra due numeri inseriti in input dall’utente per vedere come funziona.

def divide(n1, n2):
	return n1/n2
	
n1 = int(input("Inserisci il primo numero: "))
n2 = int(input("Inserisci il secondo numero: "))
res = divide(n1, n2)
print(res)

Nel caso in cui l’utente inserisca in input un valore che non rappresenta un numero intero, ad esempio un carattere, il programma scatena un errore:

Python error

Per ovviare a questo problema e gestire un errore di questo tipo possiamo utilizzare il blocco try/except come segue:

def divide(n1, n2):
	return n1/n2
	
try:
    n1 = int(input("Inserisci il primo numero: "))
    n2 = int(input("Inserisci il secondo numero: "))
    res = divide(n1, n2)
    print(res)
except:
    print("ERRORE: I valori inseriti devono essere interi!")

In questo caso invece di ottenere l’errore di esecuzione viene mostrato un messaggio personalizzato che segnala all’utente che i valori che ha inserito non sono validi.

Python error handling except

L’inserimento di un valore non numerico però non è l’unico problema che si può presentare. Se ad esempio l’utente inserisce come secondo valore uno 0, la divisione produce nuovamente un errore e non possiamo però mostrare lo stesso messaggio che indica di inserire un intero ma dobbiamo mostrare un messaggio di errore differente.
Per gestire tipi diversi di errore che possono essere scatenati dallo stesso blocco di codice occorre specificare nello statement except il tipo di errore che si vuole intercettare. In generale except senza l’indicazione del tipo di errore non deve mai essere usato!

Modifichiamo quindi il nostro codice come segue:

def divide(n1, n2):
	return n1/n2
	
try:
    n1 = int(input("Inserisci il primo numero: "))
    n2 = int(input("Inserisci il secondo numero: "))
    res = divide(n1, n2)
    print(res)
except ValueError:
    print("ERRORE: I valori inseriti devono essere interi!")
except ZeroDivisionError:
    print("ERRORE: Non si può dividere un numero per 0")

Python error handling except

In realtà in Python il costrutto try/except viene utilizzato non solo per la gestione delle eccezioni ma anche per il controllo del flusso di esecuzione del programma. Il costrutto prevede infatti un ulteriore clausola “else” che permette di definire il blocco di codice da eseguire quando l’eccezione non si verifica.

Ad esempio il blocco di codice precedente si può scrivere in maniera più pythonica nel modo seguente:

def divide(n1, n2): return n1/n2
	
try:
    n1 = int(input("Inserisci il primo numero: "))
    n2 = int(input("Inserisci il secondo numero: "))
except ValueError:
    print("ERRORE: I valori inseriti devono essere interi!")
else:
    try:
        res = divide(n1, n2)
    except ZeroDivisionError:
        print("ERRORE: Non si può dividere un numero per 0")
    else:
        print(res)

Python error handling try-except-else

Un’ulteriore clausola opzionale del costrutto try/except è “finally”, che rappresenta un blocco di codice che viene sempre eseguita sia che si verifichi un errore e quindi sia scatenata l’eccezione, sia che l’esecuzione termini normalmente.

def divide(n1, n2): return n1/n2
	
try:
    n1 = int(input("Inserisci il primo numero: "))
    n2 = int(input("Inserisci il secondo numero: "))
except ValueError:
    print("ERRORE: I valori inseriti devono essere interi!")
else:
    try:
        res = divide(n1, n2)
    except ZeroDivisionError:
        print("ERRORE: Non si può dividere un numero per 0")
    else:
        print(res)
finally:
    print("sempre eseguito!")

Python error handling try-except-else-finally
In genere nella clausola finally vengono inserite le istruzioni per il rilascio delle risorse.

2 thoughts on “Imparare Python da zero #04: eccezioni e controllo di flusso con il costrutto try-except-else-finally

  1. Pingback: Imparare Python da zero #05: leggere e scrivere file di testo | Dede Blog

  2. Pingback: Imparare Python da zero #06: ancora su files ed eccezioni e statement with | Dede Blog

Leave a Reply

Your email address will not be published. Required fields are marked *