Skip to content

Strutture Dati

Sebbene Go abbia una sintassi semplice, include diverse potenti strutture dati core. Queste strutture sono i mattoni fondamentali dei programmi Go e comprendere i loro principi di implementazione aiuta a scrivere codice più efficiente. Questo articolo presenta alcune delle strutture dati più comunemente usate in Go e le loro implementazioni sottostanti.

Strutture Dati di Base

slice Slice

Le slice sono la struttura dati più comunemente usata in Go, un'astrazione e incapsulamento degli array. Caratteristiche principali:

  • Dimensione Dinamica: la lunghezza delle slice può crescere dinamicamente
  • Semantica di Riferimento: quando una slice viene passata, viene copiata solo la struttura, non l'array sottostante
  • Meccanismo di Espansione: quando la capacità è insufficiente, si espande automaticamente

Le slice sono rappresentate a runtime dalla struttura slice, che contiene un puntatore all'array sottostante, la lunghezza e la capacità.

string Stringhe

Le stringhe sono uno dei tipi di dati più fondamentali in Go. Caratteristiche principali:

  • Immutabilità: una volta creata, una stringa non può essere modificata
  • Codifica UTF-8: generalmente rappresentano testo codificato in UTF-8
  • Sicurezza del Valore Zero: il valore zero di una stringa è la stringa vuota "", non nil

Le stringhe sono rappresentate a runtime dalla struttura stringStruct, che contiene un puntatore a un array di byte e la lunghezza.

Strutture Dati Container

map Mappe

Le map sono contenitori chiave-valore built-in in Go, implementati come tabelle hash. Caratteristiche principali:

  • Implementazione Hash Table: posiziona rapidamente gli elementi tramite funzioni hash
  • Espansione Automatica: si espande automaticamente quando il fattore di carico è troppo alto
  • Non Concurrent-Safe: la lettura/scrittura concorrente richiede meccanismi di sincronizzazione aggiuntivi

Le map sono rappresentate a runtime dalla struttura hmap, che contiene l'array di bucket, il seed hash, il conteggio degli elementi e altri campi.

syncmap Mappe Concorrenti

sync.Map è una mappa thread-safe fornita dalla libreria standard, adatta per scenari con molte letture e poche scritture. Caratteristiche principali:

  • Separazione Lettura/Scrittura: usa due map, read e dirty, per separare letture e scritture
  • Operazioni Atomiche: la read map usa operazioni atomiche, senza bisogno di lock
  • Migrazione Graduale: quando il conteggio miss raggiunge la soglia, la dirty diventa la read

sync.Map scambia spazio per tempo, offrendo prestazioni migliori rispetto a map + mutex in scenari specifici.

Strutture Dati Concorrenti

channel Canali

I channel sono il rappresentante tipico del paradigma CSP di Go, usati per la comunicazione tra goroutine. Caratteristiche principali:

  • Comunicazione tra Goroutine: passaggio di dati tra goroutine tramite channel
  • Meccanismo di Sincronizzazione: i channel senza buffer possono essere usati per sincronizzare goroutine
  • Coda con Lock: sottostante è una coda circolare con lock

I channel sono rappresentati a runtime dalla struttura hchan, che contiene un buffer circolare, code di attesa e altri campi.

select Multiplexing

select può monitorare lo stato di più channel simultaneamente, implementando il multiplexing. Caratteristiche principali:

  • Non Bloccante: può controllare in modo non bloccante se più channel sono disponibili
  • Selezione Casuale: quando più channel sono disponibili, ne seleziona uno casualmente per l'esecuzione
  • Controllo Timeout: può essere usato con time.After per implementare meccanismi di timeout

select è rappresentato a runtime dalla struttura scase per ogni branch, controllando lo stato dei channel tramite un meccanismo di polling.

Suggerimenti per l'Apprendimento

Si consiglia di seguire questo ordine di apprendimento:

  1. Iniziare con slice Slice e string Stringhe per comprendere le strutture dati di base
  2. Proseguire con map Mappe per capire l'implementazione delle tabelle hash
  3. Poi studiare channel Canali per comprendere il meccanismo di comunicazione tra goroutine
  4. Quindi apprendere select Multiplexing per padroneggiare le tecniche di multiplexing
  5. Infine studiare syncmap Mappe Concorrenti per capire l'implementazione thread-safe

Golang by www.golangdev.cn edit