ProgrammazioneSviluppatore Backend

Racconta come Go gestisce la memoria quando si passano mappe e slice alle funzioni e quali possono essere le conseguenze.

Supera i colloqui con l'assistente IA Hintsage

Risposta.

In Go, la struttura map viene sempre passata per valore, ma questo valore contiene un puntatore alle strutture interne della mappa stessa (sottoposta all'hash-table). Quindi, se si passa una mappa a una funzione e all'interno della funzione si modifica il contenuto (si aggiungono/rimuovono elementi), le modifiche saranno visibili all'esterno. Comportamenti simili hanno anche gli slice: viene copiata la struttura dello slice, ma non i dati dell'array; lo slice contiene un puntatore all'array, la lunghezza e la capacità. Se si modificano i valori per indice all'interno della funzione, anche l'array originale cambierà. Ma se all'interno della funzione si assegna un nuovo slice (ad esempio, reslice), la variabile originale non cambierà.

func updateMap(m map[string]int) { m["key"] = 42 // Le modifiche sono visibili all'esterno! } func updateSlice(s []int) { s[0] = 99 // L'array originale cambia }

Domanda insidiosa.

Perché la modifica di mappe e slice all'interno di una funzione si riflette sull'"originale"?

Risposta: Perché viene copiata solo la struttura del puntatore, mentre i dati stessi rimangono condivisi: qualsiasi modifica coinvolge lo stesso blocco di memoria.

Esempi di errori reali causati dalla mancanza di conoscenza delle sottigliezze dell'argomento.


Storia

In un progetto fintech, si passava una mappa con impostazioni di configurazione a diversi servizi, supponendo che le modifiche locali non avrebbero influenzato la mappa generale. Di conseguenza, un servizio ha modificato i valori, causando bug in altri moduli che hanno ricevuto una configurazione inaspettatamente modificata.


Storia

In un microservizio di analisi, si passava uno slice, pensando di ottenere copie indipendenti. Ma la funzione all'interno ha modificato i valori per indice, portando a dati distorti nel rapporto, poiché l'array originale è stato inaspettatamente modificato.


Storia

Nei server di gioco, si utilizzava una mappa per memorizzare le sessioni degli utenti e si passava contemporaneamente questa mappa a più goroutine. Si pensava che ogni goroutine lavorasse con la propria copia, ma in realtà si è verificata una race condition e sessioni parzialmente perse.