Dopo aver parlato dei dati e delle istruzioni, possiamo cominciare a mettere tutto assieme, per imparare a definire nuove funzioni in Python.
Queste nozioni ci serviranno anche quando parleremo delle classi; pertanto, anche se pensiamo di usare esclusivamente un approccio orientato agli oggetti, non possiamo prescindere dalla conoscenza di questo aspetto di Python.
Una caratteristica interessante di Python è il fatto che non è il linguaggio a scegliere per noi il paradigma di programmazione da usare:
procedurale, orientato agli oggetti o funzionale.
Con Python possiamo usare uno qualsiasi di questi approcci e addirittura possiamo adottare approcci misti.
Definire funzioni in Python
L’istruzione che ci permette di creare funzioni in Python è def.
Come di consueto, facciamo subito un esempio:
La funzione fact accetta un unico parametro, di nome n.
L’istruzione return viene usata per terminare la funzione restituendo il valore desiderato.
Abbiamo così implementato una funzione che restituisce il fattoriale del numero naturale passato come parametro.
Vediamo ora la funzione all’opera:
Proviamo adesso a scrivere la stessa funzione con una piccola aggiunta:
Prestiamo attenzione alla stringa che abbiamo inserito subito dopo la definizione della funzione: si tratta della stringa di documentazione.
Proviamo a digitare ora in IDLE fact seguito dalla parentesi tonda come in figura:
Possiamo notare la finestra di aiuto (il cosiddetto “helper”) che ci viene mostrata automaticamente e che include l’elenco dei parametri necessari alla funzione.
La stringa di documentazione viene salvata da Python nella variabile __doc__ che possiamo visualizzare integralmente, usando la funzione help:
Valori restituiti dalle funzioni in Python
In Python, al contrario di quanto avviene in altri linguaggi, quando una funzione termina senza l’istruzione return, viene comunque restituito il valore None.
Lo stesso accade nel caso in cui venga eseguito un return che non è seguito da un valore.
Nel seguente esempio, le funzioni f1, f2 e f3 restituiscono tutte None:
Possiamo verificarlo in IDLE:
Nel caso in cui il valore restituito da una funzione sia None, IDLE non lo mostra automaticamente:
dobbiamo richiederglielo esplicitamente con la funzione print.
Probabilmente ci sarà capitato spesso di dover fare in modo che la funzione restituisca più di un valore.
In questi casi, con linguaggi diversi da Python, si doveva ricorrere a vari escamotage: come il passaggio di parametri per riferimento, la restituzione di valori in un array e così via.
Con Python ci basta semplicemente restituire e contestualmente assegnare due o più valori.
Chiariamo con un esempio:
L’assegnamento in linea di più variabili è davvero una caratteristica utilissima di Python e può essere usata anche con sequenze come liste e tuple:
Il passaggio di parametri
Nella funzione fact di qualche paragrafo fa, abbiamo visto un esempio molto semplice, che prevedeva il passaggio di un solo parametro.
Per una funzione possiamo ovviamente definire tutti i parametri che vogliamo:
I parametri possono anche essere indicati per nome invece che per posizione.
La funzione precedente più quindi essere richiamata nei due modi seguenti:
Ma esistono altre caratteristiche e modalità per il passaggio dei parametri che ci permettono di definire le funzioni in Python in modo estremamente versatile e potente.
Parametri opzionali
Per ogni parametro possiamo definire un valore di default opzionale: in assenza del rispettivo parametro, la funzione impiegherà il valore di default.
Proviamo a digitare la sequenza “int(” in IDLE e attendere, come si può vedere nella seguente figura, la comparsa dell’helper:
Vediamo che la funzione int accetta uno o due parametri: x e base.
Visto il secondo suggerimento, possiamo intuire che il parametro base sia un parametro opzionale.
In questo caso il valore che assume il parametro opzionale è specificato.
Nel caso non vi fosse, basterebbe consultare integralmente la stringa di documentazione mediante la funzione help:
Dalla documentazione avremmo scoperto che la conversione, in assenza del parametro opzionale base, viene eseguita nel sistema decimale.
Pertanto il valore di default di base sarebbe stato 10.
Verifichiamo che in IDLE sia realmente così:
Ora proviamo a specificare esplicitamente una base:
Il valore di default è 10 e possiamo anche passarlo in modo esplicito:
Giusto per ricordarci di questa possibilità, proviamo a passare i parametri per nome, invertendo il loro ordine di definizione:
Modalità avanzate di passaggio dei parametri
In alcune situazioni particolari possiamo trovarci a dover definire funzioni in Python con un elenco di parametri non noto a priori.
Python ci permette di farlo in due modi, che possono addirittura convivere nella stessa funzione:
- *parametri trasforma una lista di parametri (senza nome e di lunghezza arbitraria) in una tupla;
- **keyword trasforma una lista di parametri (con nome e di lunghezza arbitraria) in un dizionario.
Come spesso accade in Python, un paio di esempi possono chiarirci le idee.
Cominciamo con la prima tipologia avanzata di passaggio dei parametri, la tupla di parametri posizionali:
Come possiamo vedere, l’elenco di parametri viene trasformato in una tupla, che possiamo scorrere facilmente.
Se però con la stessa funzione usiamo un parametro nominale viene sollevata un’eccezione:
Vediamo ora la seconda modalità avanzata, la tupla di parametri nominali che viene trasformata in un dizionario:
Questa volta, al contrario, se usiamo un parametro senza nome viene sollevata un’eccezione:
Ovviamente possiamo usare tutte queste modalità in un’unica funzione:
Quando queste due modalità vengono impiegate insieme, siamo obbligati a specificare prima *parametri e solo di seguito **keyword.
In caso contrario Python ci segnalerà un errore di sintassi.
Le funzioni sono oggetti
Come abbiamo visto è semplice definire funzioni in Python.
Ma una cosa fondamentale che dobbiamo ancora dire è che in Python una funzione è a tutti gli effetti un oggetto.
Possiamo assegnarla a una variabile:
O, addirittura, passarla come parametro a un’altra funzione:
Nel prossimo esempio proveremo a creare un dizionario di funzioni:
Ora utilizziamo le funzioni che abbiamo appena assegnato al nostro dizionario:
Se abbiamo un po’ più di esperienza nella programmazione, possiamo sicuramente immaginare molte situazioni in cui questa versatilità ci sarebbe tornata utile.
Riserviamo il prossimo articolo alle principali funzioni predefinite in Python, per poi dedicarci alle classi e agli input/output.
Continua a seguire la sezione dedicata alla programmazione con Python e iscriviti alla nostra newsletter!
Una risposta