Python e dizionari: indicizzare e cercare dati in modo rapido

by theArchitect
SHARE
Python e dizionari: indicizzare e cercare dati in modo rapido
© Guida-HTML5.it

Introduzione

I dizionari sono una delle strutture dati più utili di Python quando serve associare un valore a una chiave. A differenza delle liste, che richiedono una scansione sequenziale, un dizionario consente di recuperare informazioni in modo molto efficiente usando una chiave significativa, come un nome utente, un codice prodotto, un ID ordine o una sigla.

In questo tutorial vedremo un sotto-argomento pratico e molto usato: come usare i dizionari per indicizzare e cercare dati rapidamente. È un tema utile in scenari reali come:

  • ricercare un cliente partendo dal suo ID;
  • mappare codici a descrizioni;
  • trasformare una lista di record in una struttura più veloce da interrogare;
  • evitare cicli annidati quando si fanno ricerche ripetute.

Capire bene questo pattern ti aiuta a scrivere codice più pulito, più veloce e più facile da mantenere.

Codice completo

from dataclasses import dataclass
from typing import List, Dict, Optional


@dataclass
class Cliente:
    id_cliente: int
    nome: str
    email: str
    città: str


def costruisci_indice_clienti(clienti: List[Cliente]) -> Dict[int, Cliente]:
    """
    Crea un dizionario che usa l´ID cliente come chiave.
    In questo modo la ricerca diventa immediata.
    """
    indice = {}
    for cliente in clienti:
        indice[cliente.id_cliente] = cliente
    return indice


def cerca_cliente_per_id(indice_clienti: Dict[int, Cliente], id_cliente: int) -> Optional[Cliente]:
    """
    Restituisce il cliente associato all´ID richiesto.
    Se non esiste, restituisce None.
    """
    return indice_clienti.get(id_cliente)


def raggruppa_clienti_per_città(clienti: List[Cliente]) -> Dict[str, List[Cliente]]:
    """
    Esempio aggiuntivo: crea un indice per città.
    Ogni chiave è una città, ogni valore è la lista dei clienti che vivono lì.
    """
    gruppi = {}

    for cliente in clienti:
        if cliente.città not in gruppi:
            gruppi[cliente.città] = []
        gruppi[cliente.città].append(cliente)

    return gruppi


def stampa_cliente(cliente: Optional[Cliente]) -> None:
    if cliente is None:
        print("Cliente non trovato.")
        return

    print(f"ID: {cliente.id_cliente}")
    print(f"Nome: {cliente.nome}")
    print(f"Email: {cliente.email}")
    print(f"Città: {cliente.città}")


def main() -> None:
    clienti = [
        Cliente(101, "Anna Rossi", "[email protected]", "Milano"),
        Cliente(102, "Marco Bianchi", "[email protected]", "Roma"),
        Cliente(103, "Giulia Verdi", "[email protected]", "Milano"),
        Cliente(104, "Luca Neri", "[email protected]", "Torino"),
    ]

    # Costruzione dell´indice per ID
    indice_clienti = costruisci_indice_clienti(clienti)

    # Ricerca rapida
    cliente = cerca_cliente_per_id(indice_clienti, 103)
    stampa_cliente(cliente)

    print("nClienti a Milano:")
    clienti_milano = raggruppa_clienti_per_città(clienti).get("Milano", [])
    for c in clienti_milano:
        print(f"- {c.nome} ({c.email})")


if __name__ == "__main__":
    main()

Spiegazione

Il punto centrale dell’esempio è questo: invece di cercare un cliente scorrendo ogni volta tutta la lista, costruiamo un indice basato sui dizionari.

1. Dalla lista all’indice

All’inizio abbiamo una lista di oggetti Cliente. Le liste sono ottime per conservare elementi in ordine, ma non sono ideali quando devi cercare spesso un elemento specifico. Se cerchi il cliente con ID 103, senza dizionario dovresti controllare uno per uno tutti i record fino a trovarlo.

Con il dizionario invece trasformiamo i dati così:

  • chiave: l’ID cliente;
  • valore: l’oggetto Cliente.

In questo modo la ricerca diventa molto più diretta: basta usare indice_clienti.get(103).

2. Il metodo get()

Nel tutorial usiamo get() invece dell’accesso diretto con parentesi quadre. La differenza è importante:

  • indice_clienti[103] genera un errore se la chiave non esiste;
  • indice_clienti.get(103) restituisce None se la chiave manca.

Questo approccio è più sicuro quando i dati provengono da input esterni, API, file o database, perché riduce il rischio di eccezioni non gestite.

3. Raggruppare per città

La funzione raggruppa_clienti_per_città() mostra un secondo uso molto comune dei dizionari: raggruppare più elementi sotto la stessa chiave. Qui ogni città contiene una lista di clienti.

È una tecnica utile quando vuoi creare una vista organizzata dei dati, per esempio:

  • ordini per stato;
  • prodotti per categoria;
  • studenti per classe;
  • ticket per priorità.

4. Perché usare un dataclass

Abbiamo definito Cliente come dataclass perché rende il codice più leggibile. Invece di scrivere manualmente costruttori e metodi di supporto, Python genera automaticamente una struttura comoda da usare per contenere dati.

Per un tutorial sui dizionari, questa scelta aiuta a concentrarsi sul concetto principale: come indicizzare i dati.

5. Complessità e vantaggio pratico

Quando fai ricerche ripetute, il vantaggio dei dizionari diventa evidente. In generale:

  • una ricerca in lista richiede spesso una scansione lineare;
  • una ricerca in dizionario è molto più rapida nella pratica.

Questo non significa che i dizionari sostituiscano sempre le liste, ma che sono la scelta giusta quando la priorità è l’accesso veloce tramite chiave.

Best practice

  • Scegli chiavi stabili e univoche: ID, codici o email sono spesso migliori di nomi o etichette che possono cambiare.
  • Usa get() quando la chiave potrebbe non esistere: il codice diventa più robusto e leggibile.
  • Evita di sovrascrivere accidentalmente valori: se costruisci un indice con chiavi duplicate, l’ultimo elemento vince. Se non è voluto, controlla prima la presenza della chiave.
  • Se devi raggruppare, usa liste come valori: un dizionario con liste interne è spesso la soluzione più flessibile.
  • Non abusare dei dizionari per tutto: se l’ordine e la sequenza sono fondamentali, una lista può essere più adatta.
  • Usa tipi chiari: annotazioni come Dict[int, Cliente] aiutano a capire subito la struttura dei dati.

Un errore comune è usare il dizionario come semplice contenitore generico senza una chiave ben progettata. Invece, il vero valore sta nel costruire una mappa coerente tra chiave e informazione.

Riepilogo

I dizionari sono perfetti quando vuoi associare una chiave a un valore e recuperarlo rapidamente. In questo tutorial abbiamo visto come:

  • trasformare una lista di oggetti in un indice basato su ID;
  • cercare un elemento in modo semplice con get();
  • raggruppare dati sotto la stessa chiave, come clienti per città;
  • scrivere codice più pulito e più efficiente.

Se lavori spesso con dati strutturati, imparare a progettare bene i dizionari ti farà risparmiare tempo e ridurrà la complessità del codice. È una competenza fondamentale per chi sviluppa in Python in modo professionale.

Approfondisci con risorse ufficiali

SHARE