Programmazione in Python
Guida completa alla programmazione funzionale e alle strutture dati
Impara Python dalle basi: dalla sintassi fondamentale alle strutture dati avanzate. Questa guida ti accompagnerà nel mondo della programmazione funzionale con esempi pratici e spiegazioni dettagliate.
Introduzione a Python
Scopri le basi della programmazione funzionale con Python
Obiettivi del Corso
Questo corso introduce la programmazione funzionale e la programmazione in Python, fornendo una base solida per sviluppatori di tutti i livelli.
Perché Python?
Python non è un linguaggio principalmente funzionale, ma è un linguaggio multiparadigma che supporta programmazione procedurale, orientata agli oggetti e funzionale. Esistono linguaggi principalmente funzionali (OCaml, Haskell, F#), ma abbiamo scelto Python per la sua diffusione e praticità.
- Relativamente facile da imparare
- Interfacciamento con librerie C ad alte prestazioni
- Ecosistema enorme di librerie disponibili
- Supporto per diversi paradigmi di programmazione
Perché la Programmazione Funzionale?
- Base matematica: Fondata sul lambda calcolo
- Paradigma diverso: Insegna approcci alternativi alla risoluzione dei problemi
- Semplicità: Spesso porta a soluzioni più eleganti
- Parallelizzazione: Si presta meglio all'esecuzione parallela automatica
Elementi della Programmazione Funzionale
- Composizione di funzioni: I programmi sono combinazioni di funzioni
- Funzioni come oggetti: Possono essere passate come parametri e ritornate
- Immutabilità: I dati non vengono modificati, ma sostituiti con nuovi dati
- Lazy evaluation: Calcoli eseguiti solo quando necessari
Storia di Python
Le origini e l'evoluzione del linguaggio
Origini e Sviluppo
- Creatore: Guido van Rossum, programmatore olandese
- Nome: Deriva da "Monty Python's Flying Circus"
- Primo rilascio: 1991
- Versione 2.0: 2000
- Versione 3.0: 2008
Strumenti di Sviluppo
Gli ambienti per programmare in Python
Anaconda Distribution
Nel laboratorio utilizziamo Anaconda3, che include:
- Python 3.7.3 (o versioni successive)
- Jupyter Notebooks
- Spyder IDE
- Numerose librerie pre-installate
/opt/anaconda3/bin/anaconda-navigator
Jupyter Notebook
Jupyter Notebook è un'applicazione web interattiva che permette di creare e condividere documenti contenenti codice, equazioni, visualizzazioni e testo narrativo.
Caratteristiche Principali
- File .ipynb: Contengono testo e codice eseguibile
- Celle: Possono essere di tipo Markdown (testo) o Code (codice Python)
- Architettura client-server: Funziona nel browser web
- Kernel condiviso: Tutte le celle condividono lo stesso spazio di memoria
Ctrl+Enter
: Esegue la cella correnteEnter
: Entra in modalità EditEsc
: Entra in modalità Command
Spyder IDE
Spyder è un ambiente di sviluppo integrato per Python, particolarmente adatto per sviluppo scientifico e data analysis.
Interfaccia Spyder
- Pannello Editor: A sinistra, per scrivere codice
- Console IPython: In basso a destra, per esecuzione interattiva
- Pannello ausiliario: In alto a destra, con diverse tab
Shortcut | Funzione |
---|---|
F5 |
Esegue tutto il file |
Ctrl+Enter |
Esegue la cella corrente |
F9 |
Esegue la riga corrente |
Ctrl+C |
Interrompe l'esecuzione |
Strutture Dati in Python
Le collezioni di dati e le loro caratteristiche
Sequenze
Le sequenze sono collezioni ordinate di elementi. Python offre diversi tipi di sequenze, ognuna con caratteristiche specifiche.
Accesso agli Elementi
L'accesso agli elementi avviene tramite indicizzazione con parentesi quadre:
aSeq[i] # Ritorna l'i-esimo elemento della sequenza
aSeq[-1]
è l'ultimo elemento.
ls = [1, 2, 3, 4]
# Elemento 1: indice 0 o -4
# Elemento 2: indice 1 o -3
# Elemento 3: indice 2 o -2
# Elemento 4: indice 3 o -1
Operazioni Comuni
Operazione | Sintassi | Descrizione |
---|---|---|
Concatenazione | seq1 + seq2 |
Unisce due sequenze dello stesso tipo |
Ripetizione | seq * n |
Ripete la sequenza n volte |
Appartenenza | x in seq |
Verifica se x è nella sequenza |
Lunghezza | len(seq) |
Ritorna il numero di elementi |
Funzioni Utili
min(seq)
emax(seq)
: Trovano minimo e massimoseq.index(x)
: Ritorna l'indice della prima occorrenza di xseq.count(x)
: Conta le occorrenze di x
Stringhe
Le stringhe sono sequenze di caratteri. In Python non esiste il tipo "carattere" - esistono solo stringhe di lunghezza 1.
Tipi di Letterali Stringa
Tipo | Sintassi | Uso |
---|---|---|
Apici singoli | 'stringa' |
Uso generale |
Apici doppi | "stringa" |
Quando serve apice singolo interno |
Multi-linea | '''stringa''' |
Testo su più righe |
Raw string | r'path\to\file' |
Evita interpretazione caratteri escape |
f-string | f'Ciao {nome}!' |
Interpolazione di variabili |
Caratteri Speciali
\n
: Nuova riga\t
: Tab\\
: Backslash letterale\'
e\"
: Apici letterali
# Stringhe multi-linea
testo = '''Questa è una
stringa
su tre righe'''
# Raw string
percorso = r'C:\Users\nome\file.txt'
# f-string
nome = "Mario"
messaggio = f'Ciao {nome}!'
# Concatenazione automatica
risultato = "prima" "seconda" # "primaseconda"
Slicing
Lo slicing permette di estrarre porzioni di sequenze creando nuove sequenze.
Sintassi Completa
sequenza[inizio:fine:passo]
- inizio: Indice di partenza (incluso)
- fine: Indice di fine (escluso)
- passo: Incremento (default: 1)
s = "abcdefg"
# Esempi base
s[1:4] # "bcd"
s[:3] # "abc" (dall'inizio)
s[2:] # "cdefg" (fino alla fine)
s[:] # "abcdefg" (copia completa)
# Con passo
s[::2] # "aceg" (elementi pari)
s[1::2] # "bdf" (elementi dispari)
# Slicing inverso
s[::-1] # "gfedcba" (stringa invertita)
s[5:1:-1] # "fedc" (da destra a sinistra)
Liste
Le liste sono sequenze mutabili che possono contenere elementi di qualsiasi tipo.
Creazione di Liste
# Lista con elementi
numeri = [1, 2, 3, 4, 5]
# Lista mista (sconsigliata)
mista = [1, "due", 3.0, [4, 5]]
# Lista vuota
vuota = []
# Da stringa
caratteri = list("python") # ['p', 'y', 't', 'h', 'o', 'n']
Metodi Principali
Metodo | Descrizione | Esempio |
---|---|---|
append(x) |
Aggiunge elemento alla fine | lista.append(6) |
extend(seq) |
Aggiunge tutti gli elementi di seq | lista.extend([7, 8]) |
insert(i, x) |
Inserisce elemento alla posizione i | lista.insert(0, 0) |
remove(x) |
Rimuove prima occorrenza di x | lista.remove(3) |
pop(i) |
Rimuove e ritorna elemento all'indice i | elemento = lista.pop() |
clear() |
Rimuove tutti gli elementi | lista.clear() |
sort() |
Ordina la lista | lista.sort() |
reverse() |
Inverte l'ordine | lista.reverse() |
Unpacking con Asterisco
numeri = [1, 2, 3, 4, 5]
# Unpacking base
primo, secondo = [1, 2]
# Con asterisco
primo, *resto = numeri # primo=1, resto=[2,3,4,5]
*inizio, ultimo = numeri # inizio=[1,2,3,4], ultimo=5
primo, *mezzo, ultimo = numeri # primo=1, mezzo=[2,3,4], ultimo=5
Assegnamento a Slice
Le liste supportano l'assegnamento diretto a slice, permettendo di modificare porzioni della lista:
lista = [1, 2, 3, 4, 5]
# Sostituisce elementi
lista[1:4] = [7, 8] # [1, 7, 8, 5]
# Cambia lunghezza
lista[2:] = [9, 10, 11] # [1, 7, 9, 10, 11]
# Slice esteso (passo > 1)
lista[::2] = [0, 0, 0] # Sostituisce elementi a posizioni pari
lista[:]
o lista.copy()
per creare una copia.
Tuple
Le tuple sono sequenze immutabili, spesso utilizzate per dati eterogenei.
Creazione di Tuple
# Con parentesi
coordinate = (10, 20)
persona = ("Mario", 30, "Roma")
# Senza parentesi
punto = 1, 2, 3
# Tupla vuota
vuota = ()
# Tupla con un elemento (nota la virgola!)
singleton = (42,)
# Da lista
da_lista = tuple([1, 2, 3])
(42,)
. Altrimenti (42)
è solo un numero tra parentesi.
Utilizzo delle Tuple
- Coordinate:
(x, y, z)
- Dati eterogenei:
(nome, età, città)
- Chiavi di dizionario: Se contengono solo dati immutabili
- Valori di ritorno multipli:
return nome, età
Set
I set sono collezioni non ordinate di elementi unici, utili per operazioni insiemistiche.
Creazione di Set
# Con parentesi graffe
numeri = {1, 2, 3, 4, 5}
# Rimuove duplicati automaticamente
unici = {1, 2, 3, 2, 3, 1} # {1, 2, 3}
# Set vuoto (non {})
vuoto = set()
# Da lista
da_lista = set([1, 2, 2, 3]) # {1, 2, 3}
{}
crea un dizionario vuoto, non un set. Per un set vuoto usa set()
.
Operazioni Insiemistiche
Operazione | Operatore | Metodo | Descrizione |
---|---|---|---|
Unione | | |
union() |
Elementi in almeno uno dei set |
Intersezione | & |
intersection() |
Elementi in entrambi i set |
Differenza | - |
difference() |
Elementi nel primo ma non nel secondo |
Diff. simmetrica | ^ |
symmetric_difference() |
Elementi in uno solo dei due set |
set1 = {1, 2, 3, 4}
set2 = {3, 4, 5, 6}
print(set1 | set2) # {1, 2, 3, 4, 5, 6} - Unione
print(set1 & set2) # {3, 4} - Intersezione
print(set1 - set2) # {1, 2} - Differenza
print(set1 ^ set2) # {1, 2, 5, 6} - Differenza simmetrica
Dizionari
I dizionari sono collezioni di coppie chiave-valore, ottimizzate per l'accesso rapido tramite chiave.
Creazione di Dizionari
# Sintassi base
studente = {
"nome": "Mario",
"età": 20,
"corso": "Informatica"
}
# Dizionario vuoto
vuoto = {}
# Con funzione dict()
da_coppie = dict([('a', 1), ('b', 2)])
con_keywords = dict(nome="Mario", età=20)
Accesso e Modifica
# Accesso
print(studente["nome"]) # Mario
print(studente.get("voto", 0)) # 0 (default se chiave non esiste)
# Modifica
studente["voto"] = 28
studente["età"] = 21
# Verifica esistenza
if "nome" in studente:
print("Nome presente")
Metodi Principali
Metodo | Descrizione | Esempio |
---|---|---|
keys() |
Ritorna le chiavi | list(dict.keys()) |
values() |
Ritorna i valori | list(dict.values()) |
items() |
Ritorna coppie chiave-valore | list(dict.items()) |
get(key, default) |
Accesso sicuro con default | dict.get("chiave", "N/A") |
pop(key) |
Rimuove e ritorna valore | valore = dict.pop("chiave") |
update(other) |
Aggiorna con altro dizionario | dict.update({"nuovo": "valore"}) |
Iterazione
# Sulle chiavi (default)
for chiave in dizionario:
print(chiave)
# Su chiavi e valori
for chiave, valore in dizionario.items():
print(f"{chiave}: {valore}")
# Solo sui valori
for valore in dizionario.values():
print(valore)
Funzioni di Conversione
Le funzioni di conversione creano nuovi oggetti del tipo desiderato senza modificare quelli originali.
Conversioni Principali
Funzione | Da | A | Esempio |
---|---|---|---|
int() |
str, float, bool | int | int("42") → 42 |
float() |
str, int, bool | float | float("3.14") → 3.14 |
str() |
qualsiasi | str | str([1,2,3]) → "[1, 2, 3]" |
list() |
str, tuple, set | list | list("abc") → ['a', 'b', 'c'] |
tuple() |
str, list, set | tuple | tuple([1,2,3]) → (1, 2, 3) |
set() |
str, list, tuple | set | set([1,1,2]) → {1, 2} |
dict() |
liste di coppie | dict | dict([('a',1), ('b',2)]) |
Conversioni Speciali
Funzione | Descrizione | Esempio |
---|---|---|
ord() |
Carattere → codice ASCII | ord('A') → 65 |
chr() |
Codice ASCII → carattere | chr(65) → 'A' |
hex() |
Intero → esadecimale | hex(255) → '0xff' |
bin() |
Intero → binario | bin(8) → '0b1000' |
oct() |
Intero → ottale | oct(8) → '0o10' |
# Conversioni numeriche
print(float(True)) # 1.0
print(int("321") + 4) # 325
# Conversioni di strutture dati
print(list({'a': 1, 'b': 2})) # ['a', 'b'] (solo chiavi)
print(list("PYTHON")) # ['P', 'Y', 'T', 'H', 'O', 'N']
# Conversioni speciali
print(hex(20)) # 0x14
print(chr(69)) # E
Conclusioni
Il tuo percorso di apprendimento Python inizia qui
Complimenti!
Hai completato la guida introduttiva a Python e alle sue strutture dati. Ora hai le basi per iniziare a programmare in Python con fiducia!
Risorse Aggiuntive
-
"Programmare con Python Guida completa" di Marco Buttu
-
"Functional Python Programming" di Steven Lott
-
Documentazione ufficiale Python docs.python.org